def list_labs(self, public_identifier): rlms_db = self.session.query(RLMS).filter_by( public_identifier=public_identifier, publicly_available=True).first() if rlms_db is None: return self.render("public/errors.html", message="RLMS not found") RLMS_CLASS = get_manager_class(rlms_db.kind, rlms_db.version, rlms_db.id) rlms = RLMS_CLASS(rlms_db.configuration) query = request.args.get('q') if query is not None: page = request.args.get('p', '1') try: page = int(page) except: page = 1 else: page = 1 RLMS_CLASS = get_manager_class(rlms_db.kind, rlms_db.version, rlms_db.id) rlms = RLMS_CLASS(rlms_db.configuration) if query: query_results = rlms.search(query=query, page=page) labs = query_results['laboratories'] force_search = False number_of_pages = query_results.get('pages', 1) pages = [] if number_of_pages > 1: for p in xrange(1, number_of_pages + 1): obj = { 'label': unicode(p), 'link': url_for('.list_labs', public_identifier=public_identifier, q=query, p=p) } obj['active'] = (p != page) pages.append(obj) else: query_results = {} labs = rlms.get_laboratories() capabilities = rlms.get_capabilities() force_search = Capabilities.FORCE_SEARCH in capabilities pages = [] return self.render("public/list_labs.html", rlms=rlms_db, labs=labs, query=query, force_search=force_search, pages=pages, page=page, public_identifier=public_identifier)
def launch_experiment(): consumer_key = session.get('consumer') if consumer_key is None: return gettext("consumer key not found") permission_to_lt_user = PermissionToLtUser.find(key = consumer_key) if permission_to_lt_user is None: return gettext("permission not found") p_to_lt = permission_to_lt_user.permission_to_lt courses_configurations = [] # No such concept in the LTI version request_payload = {} # This could be populated in the HTML. Pending. lt_configuration = p_to_lt.configuration db_laboratory = p_to_lt.laboratory db_rlms = db_laboratory.rlms author = session.get('author_identifier', '(not in session)') referer = request.referrer ManagerClass = get_manager_class(db_rlms.kind, db_rlms.version) remote_laboratory = ManagerClass(db_rlms.configuration) response = remote_laboratory.reserve(db_laboratory.laboratory_id, author, p_to_lt.lt.name, lt_configuration, courses_configurations, request_payload, { 'user_agent' : unicode(request.user_agent), 'from_ip' : request.remote_addr, 'referer' : referer, }) load_url = response['load_url'] return redirect(load_url)
def launch_lab(self): lab_id = request.args.get('id') lab = self.session.query(Laboratory).filter_by(id=lab_id).first() if lab is None: return "Laboratory id not found", 404 db_rlms = lab.rlms ManagerClass = get_manager_class(db_rlms.kind, db_rlms.version, db_rlms.id) remote_laboratory = ManagerClass(db_rlms.configuration) back_url = url_for('.display_lab', id=lab_id) try: response = remote_laboratory.reserve( lab.laboratory_id, current_user.login, "admin-panel", "{}", [], {}, { 'user_agent': unicode(request.user_agent), 'from_ip': remote_addr(), 'referer': request.referrer, }, back_url=back_url, debug=True) load_url = response['load_url'] except Exception as e: flash( gettext( "There was a problem testing this experiment. Error message: %s" % e)) return redirect(back_url) return redirect(load_url)
def launch_lab(self): lab_id = request.args.get('id') lab = self.session.query(Laboratory).filter_by(id = lab_id).first() if lab is None: return "Laboratory id not found", 404 db_rlms = lab.rlms ManagerClass = get_manager_class(db_rlms.kind, db_rlms.version, db_rlms.id) remote_laboratory = ManagerClass(db_rlms.configuration) back_url = url_for('.display_lab', id = lab_id) try: response = remote_laboratory.reserve(lab.laboratory_id, current_user.login, "admin-panel", "{}", [], {}, { 'user_agent' : unicode(request.user_agent), 'from_ip' : remote_addr(), 'referer' : request.referrer, }, back_url = back_url, debug = True) load_url = response['load_url'] except Exception as e: flash(gettext("There was a problem testing this experiment. Error message: %s" % e)) return redirect(back_url) return redirect(load_url)
def list_widgets(self, rlms_identifier, lab_identifier): rlms_db = self.session.query(RLMS).filter_by(public_identifier = rlms_identifier, publicly_available = True).first() if rlms_db is None: return self.render("public/errors.html", message = "RLMS not found") RLMS_CLASS = get_manager_class(rlms_db.kind, rlms_db.version, rlms_db.id) rlms = RLMS_CLASS(rlms_db.configuration) if Capabilities.WIDGET in rlms.get_capabilities(): widgets = rlms.list_widgets(lab_identifier) else: widgets = [ { 'name' : 'lab', 'description' : 'Main view of the laboratory' } ] autoload = rlms_db.default_autoload # XXX: TODO: check if the lab_identifier does not exist and report it! links = { # widget-name : link } for widget in widgets: link = url_for('opensocial.public_rlms_widget_html', rlms_identifier = rlms_identifier, lab_name = lab_identifier, widget_name = widget['name'], _external = True) links[widget['name']] = link list_widgets_kwargs = dict(rlms_identifier = rlms_identifier, lab_identifier = lab_identifier, _external = True) return self.render("public/list_widgets.html", list_widgets_kwargs = list_widgets_kwargs, widgets = widgets, lab_name = lab_identifier, links = links, autoload = autoload)
def admin_rlms_rlms_list_external(rlmstype, rlmsversion, id): rlms = db_session.query(RLMS).filter_by(id = id).first() if rlms is None or rlms.rlms_version.version != rlmsversion or rlms.rlms_version.rlms_type.name != rlmstype: return render_template("labmanager_admin/rlms_errors.html") existing_laboratory_ids = [ laboratory.laboratory_id for laboratory in rlms.laboratories ] ManagerClass = get_manager_class(rlmstype, rlmsversion) manager_class = ManagerClass(rlms.configuration) try: available_laboratories = manager_class.get_laboratories() except: traceback.print_exc() flash("There was an error retrieving laboratories. Check the trace") return render_template("labmanager_admin/rlms_errors.html") available_laboratory_ids = [ lab.laboratory_id for lab in available_laboratories ] if request.method == 'POST': if request.form.get('action','') == 'add': for laboratory_id in request.form: if laboratory_id != 'action' and laboratory_id in available_laboratory_ids and laboratory_id not in existing_laboratory_ids: new_lab = Laboratory(laboratory_id, laboratory_id, rlms) db_session.add(new_lab) db_session.commit() return redirect(url_for('admin_rlms_rlms_list', rlmstype = rlmstype, rlmsversion = rlmsversion, id = id)) return render_template("labmanager_admin/rlms_rlms_list_external.html", available_laboratories = available_laboratories, type_name = rlmstype, version = rlmsversion, rlms_name = rlms.name, existing_laboratory_ids = existing_laboratory_ids)
def _open_widget_impl(lab_name, widget_name, public_lab = False, public_rlms = False, institution_id = None, rlms_identifier = None): if public_rlms: db_rlms = db.session.query(RLMS).filter_by(publicly_available = True, public_identifier = rlms_identifier).first() if db_rlms is None: return gettext("RLMS not found") else: if public_lab: db_laboratory = db.session.query(Laboratory).filter_by(publicly_available = True, public_identifier = lab_name).first() else: institution = db.session.query(LearningTool).filter_by(name = institution_id).first() if institution is None or len(institution.shindig_credentials) == 0: return gettext("Institution not found or it does not support Shindig") permission = db.session.query(PermissionToLt).filter_by(lt = institution, local_identifier = lab_name).first() db_laboratory = permission.laboratory if permission is not None else None if db_laboratory is None: return gettext("Laboratory not found") db_rlms = db_laboratory.rlms rlms_version = db_rlms.version rlms_kind = db_rlms.kind ManagerClass = get_manager_class(rlms_kind, rlms_version, db_rlms.id) remote_laboratory = ManagerClass(db_rlms.configuration) reservation_id = request.args.get('reservation_id') or 'reservation-id-not-found' locale = request.args.get('locale') or None kwargs = {} if locale: kwargs['locale'] = locale if Capabilities.WIDGET in remote_laboratory.get_capabilities(): response = remote_laboratory.load_widget(reservation_id, widget_name, back = url_for('.reload', _external = True), **kwargs) else: response = {'url' : reservation_id} widget_contents_url = response['url'] return redirect(widget_contents_url)
def list_widgets(self, public_identifier): laboratory = self.session.query(Laboratory).filter_by(public_identifier = public_identifier, publicly_available = True).first() if laboratory is None: return self.render("public/errors.html", message = "Laboratory not found") rlms_db = laboratory.rlms RLMS_CLASS = get_manager_class(rlms_db.kind, rlms_db.version, rlms_db.id) rlms = RLMS_CLASS(rlms_db.configuration) if Capabilities.WIDGET in rlms.get_capabilities(): widgets = rlms.list_widgets(laboratory.laboratory_id) else: widgets = [ { 'name' : 'lab', 'description' : 'Main view of the laboratory' } ] autoload = rlms_db.default_autoload links = { # widget-name : link } for widget in widgets: link = url_for('opensocial.public_widget_xml', lab_name = public_identifier, widget_name = widget['name'], _external = True) if link.startswith('https://'): link = link.replace('https://', 'http://', 1) links[widget['name']] = link list_widgets_kwargs = dict(public_identifier = public_identifier, _external = True) return self.render("public/list_widgets.html", list_widgets_kwargs = list_widgets_kwargs, widgets = widgets, lab_name = public_identifier, links = links, autoload = autoload)
def list_widgets(self, local_identifier): laboratory = self.session.query(Laboratory).join(PermissionToLt).filter_by(lt = current_user.lt, local_identifier = local_identifier).first() if laboratory is None: return self.render("ple_admin/errors.html", message = gettext("Laboratory not found")) rlms_db = laboratory.rlms RLMS_CLASS = get_manager_class(rlms_db.kind, rlms_db.version) rlms = RLMS_CLASS(rlms_db.configuration) widgets = rlms.list_widgets(laboratory.laboratory_id) return self.render("ple_admin/list_widgets.html", widgets = widgets, institution_id = current_user.lt.name, lab_name = local_identifier)
def list_labs(self, public_identifier): rlms_db = self.session.query(RLMS).filter_by(public_identifier = public_identifier, publicly_available = True).first() if rlms_db is None: return self.render("public/errors.html", message = "RLMS not found") RLMS_CLASS = get_manager_class(rlms_db.kind, rlms_db.version, rlms_db.id) rlms = RLMS_CLASS(rlms_db.configuration) query = request.args.get('q') if query is not None: page = request.args.get('p', '1') try: page = int(page) except: page = 1 else: page = 1 RLMS_CLASS = get_manager_class(rlms_db.kind, rlms_db.version, rlms_db.id) rlms = RLMS_CLASS(rlms_db.configuration) if query: query_results = rlms.search(query = query, page = page) labs = query_results['laboratories'] force_search = False number_of_pages = query_results.get('pages', 1) pages = [] if number_of_pages > 1: for p in xrange(1, number_of_pages + 1): obj = { 'label' : unicode(p), 'link' : url_for('.list_labs', public_identifier = public_identifier, q = query, p = p) } obj['active'] = (p != page) pages.append(obj) else: query_results = {} labs = rlms.get_laboratories() capabilities = rlms.get_capabilities() force_search = Capabilities.FORCE_SEARCH in capabilities pages = [] return self.render("public/list_labs.html", rlms = rlms_db, labs = labs, query = query, force_search = force_search, pages = pages, page = page, public_identifier = public_identifier)
def plugin_setup(self, rlms_id): rlms_obj = self.session.query(RLMS).filter_by(id = rlms_id).first() if not rlms_obj: return "RLMS not found", 404 if rlms_obj.kind != http_plugin.PLUGIN_NAME: return "RLMS is not HTTP", 400 ManagerClass = get_manager_class(rlms_obj.kind, rlms_obj.version) rlms_instance = ManagerClass(rlms_obj.configuration) back_url = url_for('.edit_view', id = rlms_id, _external = True) setup_url = rlms_instance.setup(back_url = back_url) return redirect(setup_url)
def show_lab(self, public_identifier): lab = self.session.query(Laboratory).filter_by( public_identifier=public_identifier).first() if lab is None: return "Laboratory id not found", 404 if request.method == 'GET': return self.render("public/display_public_lab.html", laboratory=lab) # Else is post db_rlms = lab.rlms ManagerClass = get_manager_class(db_rlms.kind, db_rlms.version, db_rlms.id) remote_laboratory = ManagerClass(db_rlms.configuration) back_url = url_for('.show_lab', public_identifier=public_identifier, _external=True) next_url = request.args.get('return') if next_url: for url in current_app.config.get('VALID_REDIRECT_URLS') or []: if next_url.startswith(url): back_url = next_url break try: response = remote_laboratory.reserve( lab.laboratory_id, "anonymous", "admin-panel", "{}", [], {}, { 'user_agent': unicode(request.user_agent), 'from_ip': remote_addr(), 'referer': request.referrer, }, back_url=back_url, debug=True) load_url = response['load_url'] except Exception as e: import traceback traceback.print_exc() flash( gettext( "There was a problem testing this experiment. Error message: %s" % e)) return redirect(back_url) return redirect(load_url)
def list_widgets(self, local_identifier): laboratory = self.session.query(Laboratory).join( PermissionToLt).filter_by( lt=current_user.lt, local_identifier=local_identifier).first() if laboratory is None: return self.render("ple_admin/errors.html", message=gettext("Laboratory not found")) rlms_db = laboratory.rlms RLMS_CLASS = get_manager_class(rlms_db.kind, rlms_db.version, rlms_db.id) rlms = RLMS_CLASS(rlms_db.configuration) widgets = rlms.list_widgets(laboratory.laboratory_id) return self.render("ple_admin/list_widgets.html", widgets=widgets, institution_id=current_user.lt.name, lab_name=local_identifier)
def _extract_widget_config(rlms_db, laboratory_identifier, widget_name, lab_found): autoload = None if request.args.get('autoload'): autoload = request.args['autoload'].lower() == 'true' height = None if request.args.get('height'): try: height = '%spx' % int(request.args['height']) except: pass base_data = {} if height is not None: base_data['height'] = height if not lab_found: return base_data RLMS_CLASS = get_manager_class(rlms_db.kind, rlms_db.version) rlms = RLMS_CLASS(rlms_db.configuration) if Capabilities.FORCE_SEARCH in rlms.get_capabilities(): if autoload is None: autoload = True # By default in those cases where a search is mandatory else: labs = [ lab for lab in rlms.get_laboratories() if lab.laboratory_id == laboratory_identifier ] if not labs: # The laboratory has changed return None if autoload is None: autoload = labs[0].autoload widgets = rlms.list_widgets(laboratory_identifier) for widget in widgets: if widget['name'] == widget_name: widget['autoload'] = autoload if height is not None: widget['height'] = height return widget base_data['autoload'] = autoload return base_data
def plugin_setup(self, rlms_id): rlms_obj = self.session.query(RLMS).filter_by(id = rlms_id).first() if not rlms_obj: return "RLMS not found", 404 if rlms_obj.kind != http_plugin.PLUGIN_NAME: return "RLMS is not HTTP", 400 ManagerClass = get_manager_class(rlms_obj.kind, rlms_obj.version, rlms_obj.id) rlms_instance = ManagerClass(rlms_obj.configuration) back_url = url_for('.edit_view', id = rlms_id, _external = True) try: setup_url = rlms_instance.setup(back_url = back_url) except Exception as e: flash(gettext("Couldn't load the setup URL! (this usually means that the plug-in is not correctly configured). Error message: %s" % e)) return redirect(back_url) else: return redirect(setup_url)
def list_widgets(self, rlms_identifier, lab_identifier): rlms_db = self.session.query(RLMS).filter_by( public_identifier=rlms_identifier, publicly_available=True).first() if rlms_db is None: return self.render("public/errors.html", message="RLMS not found") RLMS_CLASS = get_manager_class(rlms_db.kind, rlms_db.version, rlms_db.id) rlms = RLMS_CLASS(rlms_db.configuration) if Capabilities.WIDGET in rlms.get_capabilities(): widgets = rlms.list_widgets(lab_identifier) else: widgets = [{ 'name': 'lab', 'description': 'Main view of the laboratory' }] autoload = rlms_db.default_autoload # XXX: TODO: check if the lab_identifier does not exist and report it! links = { # widget-name : link } for widget in widgets: link = url_for('opensocial.public_rlms_widget_xml', rlms_identifier=rlms_identifier, lab_name=lab_identifier, widget_name=widget['name'], _external=True) if link.startswith('https://'): link = link.replace('https://', 'http://', 1) links[widget['name']] = link list_widgets_kwargs = dict(rlms_identifier=rlms_identifier, lab_identifier=lab_identifier, _external=True) return self.render("public/list_widgets.html", list_widgets_kwargs=list_widgets_kwargs, widgets=widgets, lab_name=lab_identifier, links=links, autoload=autoload)
def _rlms_to_translations(rlms_db, laboratory_id, language): translations = {} if rlms_db is not None: RLMS_CLASS = get_manager_class(rlms_db.kind, rlms_db.version, rlms_db.id) rlms = RLMS_CLASS(rlms_db.configuration) capabilities = rlms.get_capabilities() if Capabilities.TRANSLATIONS in capabilities: translations = rlms.get_translations(laboratory_id) if 'translations' not in translations: translations['translations'] = {} for lang in DEFAULT_TRANSLATIONS: # don't add empty translations if lang in translations['translations']: translations['translations'][lang].update(DEFAULT_TRANSLATIONS[lang]) translations_xml = _translations_to_xml(translations, language) return Response(translations_xml, mimetype='application/xml')
def list_widgets(self, public_identifier): laboratory = self.session.query(Laboratory).filter_by(public_identifier = public_identifier, publicly_available = True).first() if laboratory is None: return self.render("public/errors.html", message = "Laboratory not found") rlms_db = laboratory.rlms RLMS_CLASS = get_manager_class(rlms_db.kind, rlms_db.version) rlms = RLMS_CLASS(rlms_db.configuration) widgets = rlms.list_widgets(laboratory.laboratory_id) links = { # widget-name : link } for widget in widgets: link = url_for('opensocial.public_widget_xml', lab_name = public_identifier, widget_name = widget['name'], _external = True) if link.startswith('https://'): link = link.replace('https://', 'http://', 1) links[widget['name']] = link list_widgets_kwargs = dict(public_identifier = public_identifier, _external = True) return self.render("public/list_widgets.html", list_widgets_kwargs = list_widgets_kwargs, widgets = widgets, lab_name = public_identifier, links = links)
def admin_rlms_rlms_list_external(rlmstype, rlmsversion, id): rlms = db_session.query(RLMS).filter_by(id=id).first() if rlms is None or rlms.rlms_version.version != rlmsversion or rlms.rlms_version.rlms_type.name != rlmstype: return render_template("labmanager_admin/rlms_errors.html") existing_laboratory_ids = [ laboratory.laboratory_id for laboratory in rlms.laboratories ] ManagerClass = get_manager_class(rlmstype, rlmsversion) manager_class = ManagerClass(rlms.configuration) try: available_laboratories = manager_class.get_laboratories() except: traceback.print_exc() flash("There was an error retrieving laboratories. Check the trace") return render_template("labmanager_admin/rlms_errors.html") available_laboratory_ids = [ lab.laboratory_id for lab in available_laboratories ] if request.method == 'POST': if request.form.get('action', '') == 'add': for laboratory_id in request.form: if laboratory_id != 'action' and laboratory_id in available_laboratory_ids and laboratory_id not in existing_laboratory_ids: new_lab = Laboratory(laboratory_id, laboratory_id, rlms) db_session.add(new_lab) db_session.commit() return redirect( url_for('admin_rlms_rlms_list', rlmstype=rlmstype, rlmsversion=rlmsversion, id=id)) return render_template("labmanager_admin/rlms_rlms_list_external.html", available_laboratories=available_laboratories, type_name=rlmstype, version=rlmsversion, rlms_name=rlms.name, existing_laboratory_ids=existing_laboratory_ids)
def list_widgets(self, rlms_identifier, lab_identifier): rlms_db = self.session.query(RLMS).filter_by(public_identifier = rlms_identifier, publicly_available = True).first() if rlms_db is None: return self.render("public/errors.html", message = "RLMS not found") RLMS_CLASS = get_manager_class(rlms_db.kind, rlms_db.version) rlms = RLMS_CLASS(rlms_db.configuration) widgets = rlms.list_widgets(lab_identifier) # XXX: TODO: check if the lab_identifier does not exist and report it! links = { # widget-name : link } for widget in widgets: link = url_for('opensocial.public_rlms_widget_xml', rlms_identifier = rlms_identifier, lab_name = lab_identifier, widget_name = widget['name'], _external = True) if link.startswith('https://'): link = link.replace('https://', 'http://', 1) links[widget['name']] = link list_widgets_kwargs = dict(rlms_identifier = rlms_identifier, lab_identifier = lab_identifier, _external = True) return self.render("public/list_widgets.html", list_widgets_kwargs = list_widgets_kwargs, widgets = widgets, lab_name = lab_identifier, links = links)
def show_lab(self, public_identifier): lab = self.session.query(Laboratory).filter_by(public_identifier = public_identifier).first() if lab is None: return "Laboratory id not found", 404 if request.method == 'GET': return self.render("public/display_public_lab.html", laboratory = lab) # Else is post db_rlms = lab.rlms ManagerClass = get_manager_class(db_rlms.kind, db_rlms.version, db_rlms.id) remote_laboratory = ManagerClass(db_rlms.configuration) back_url = url_for('.show_lab', public_identifier=public_identifier, _external=True) next_url = request.args.get('return') if next_url: for url in current_app.config.get('VALID_REDIRECT_URLS') or []: if next_url.startswith(url): back_url = next_url break try: response = remote_laboratory.reserve(lab.laboratory_id, "anonymous", "admin-panel", "{}", [], {}, { 'user_agent' : unicode(request.user_agent), 'from_ip' : remote_addr(), 'referer' : request.referrer, }, back_url = back_url, debug = True) load_url = response['load_url'] except Exception as e: import traceback traceback.print_exc() flash(gettext("There was a problem testing this experiment. Error message: %s" % e)) return redirect(back_url) return redirect(load_url)
def launch_experiment(): consumer_key = session.get('consumer') if consumer_key is None: return gettext("consumer key not found") permission_to_lt_user = PermissionToLtUser.find(key = consumer_key) if permission_to_lt_user is None: return gettext("permission not found") p_to_lt = permission_to_lt_user.permission_to_lt courses_configurations = [] # No such concept in the LTI version request_payload = {} # This could be populated in the HTML. Pending. lt_configuration = p_to_lt.configuration db_laboratory = p_to_lt.laboratory db_rlms = db_laboratory.rlms author = session.get('author_identifier', '(not in session)') referer = request.referrer ManagerClass = get_manager_class(db_rlms.kind, db_rlms.version, db_rlms.id) remote_laboratory = ManagerClass(db_rlms.configuration) request_info = { 'user_agent' : unicode(request.user_agent), 'from_ip' : remote_addr(), 'referer' : referer, } for key in 'group_name', 'group_id', 'user_fullname': if key in session: request_info[key] = session[key] kwargs = {} if 'launch_locale' in session: kwargs['locale'] = session['launch_locale'].split('-')[0].split('_')[0] response = remote_laboratory.reserve(db_laboratory.laboratory_id, author, p_to_lt.lt.name, lt_configuration, courses_configurations, request_payload, request_info, **kwargs) load_url = response['load_url'] return redirect(load_url)
def admin_rlms_rlms_list(rlmstype, rlmsversion, id): rlms = db_session.query(RLMS).filter_by(id = id).first() if rlms is None or rlms.rlms_version.version != rlmsversion or rlms.rlms_version.rlms_type.name != rlmstype: return render_template("labmanager_admin/rlms_errors.html") if request.method == 'POST': if request.form.get('action','') == 'add': return redirect(url_for('admin_rlms_rlms_list_external', rlmstype = rlmstype, rlmsversion = rlmsversion, id = id)) laboratories = rlms.laboratories ManagerClass = get_manager_class(rlmstype, rlmsversion) manager_class = ManagerClass(rlms.configuration) try: confirmed_laboratories = manager_class.get_laboratories() except: traceback.print_exc() flash("There was an error retrieving laboratories. Check the trace") return render_template("labmanager_admin/rlms_errors.html") confirmed_laboratory_ids = [ confirmed_laboratory.laboratory_id for confirmed_laboratory in confirmed_laboratories ] return render_template("labmanager_admin/rlms_rlms_list.html", laboratories = laboratories, type_name = rlmstype, version = rlmsversion, rlms_name = rlms.name, confirmed_laboratory_ids = confirmed_laboratory_ids, rlms_id = rlms.id)
def launch_experiment(): consumer_key = session.get('consumer') if consumer_key is None: return gettext("consumer key not found") permission_to_lt_user = PermissionToLtUser.find(key=consumer_key) if permission_to_lt_user is None: return gettext("permission not found") p_to_lt = permission_to_lt_user.permission_to_lt courses_configurations = [] # No such concept in the LTI version request_payload = {} # This could be populated in the HTML. Pending. lt_configuration = p_to_lt.configuration db_laboratory = p_to_lt.laboratory db_rlms = db_laboratory.rlms author = session.get('author_identifier', '(not in session)') referer = request.referrer ManagerClass = get_manager_class(db_rlms.kind, db_rlms.version, db_rlms.id) remote_laboratory = ManagerClass(db_rlms.configuration) request_info = { 'user_agent': unicode(request.user_agent), 'from_ip': remote_addr(), 'referer': referer, } for key in 'group_name', 'group_id', 'user_fullname': if key in session: request_info[key] = session[key] kwargs = {} if 'launch_locale' in session: kwargs['locale'] = session['launch_locale'].split('-')[0].split('_')[0] response = remote_laboratory.reserve(db_laboratory.laboratory_id, author, p_to_lt.lt.name, lt_configuration, courses_configurations, request_payload, request_info, **kwargs) load_url = response['load_url'] return redirect(load_url)
def admin_rlms_rlms_list(rlmstype, rlmsversion, id): rlms = db_session.query(RLMS).filter_by(id=id).first() if rlms is None or rlms.rlms_version.version != rlmsversion or rlms.rlms_version.rlms_type.name != rlmstype: return render_template("labmanager_admin/rlms_errors.html") if request.method == 'POST': if request.form.get('action', '') == 'add': return redirect( url_for('admin_rlms_rlms_list_external', rlmstype=rlmstype, rlmsversion=rlmsversion, id=id)) laboratories = rlms.laboratories ManagerClass = get_manager_class(rlmstype, rlmsversion) manager_class = ManagerClass(rlms.configuration) try: confirmed_laboratories = manager_class.get_laboratories() except: traceback.print_exc() flash("There was an error retrieving laboratories. Check the trace") return render_template("labmanager_admin/rlms_errors.html") confirmed_laboratory_ids = [ confirmed_laboratory.laboratory_id for confirmed_laboratory in confirmed_laboratories ] return render_template("labmanager_admin/rlms_rlms_list.html", laboratories=laboratories, type_name=rlmstype, version=rlmsversion, rlms_name=rlms.name, confirmed_laboratory_ids=confirmed_laboratory_ids, rlms_id=rlms.id)
def _add_or_edit(self, rlms, version, add_or_edit, obj, config): edit_id = request.args.get('id') form_class = get_form_class(rlms, version) form = form_class(add_or_edit=add_or_edit, obj=obj) error_messages = [] if form.validate_on_submit(): configuration = config for key in form.get_field_names(): if key not in dir(forms.AddForm): field = getattr(form, key) is_password = '******' in unicode(field.type).lower() # If we're editing, and this field is a password, do not change it if is_password and not add_or_edit and field.data == '': continue configuration[key] = field.data config_json = json.dumps(configuration) current_rlms_id = None if add_or_edit else edit_id ManagerClass = get_manager_class(rlms, version, current_rlms_id) rlms_instance = ManagerClass(config_json) if hasattr(rlms_instance, 'test'): try: error_messages = rlms_instance.test() or [] except Exception as e: error_messages.append( u'%s%s' % (gettext("Error testing the RLMS:"), e)) traceback.print_exc() if form.publicly_available.data and len( form.public_identifier.data) == 0: form.public_identifier.errors = [ gettext( "If the RLMS is public, it must have a public identifier" ) ] error_messages.append(gettext("Invalid public identifier")) elif form.publicly_available.data and len( form.public_identifier.data) < 4: form.public_identifier.errors = [ gettext( "If the RLMS is public, it must have a public identifier with at least 4 characters" ) ] error_messages.append(gettext("Invalid public identifier")) elif form.publicly_available.data: # If publicly available, retrieve existing RLMS with that public identifier existing_objects = self.session.query(RLMS).filter_by( public_identifier=form.public_identifier.data).all() if not add_or_edit: # If editing, don't count the one being edited existing_objects = [ existing_obj for existing_obj in existing_objects if unicode(existing_obj.id) != unicode(edit_id) ] if existing_objects: form.public_identifier.errors = [ gettext("That identifier is already taken") ] error_messages.append( gettext( "Use other identifier or don't make the RLMS public" )) if not error_messages: if add_or_edit: rlms_obj = RLMS( kind=rlms, version=version, name=form.name.data, url=form.url.data, location=form.location.data, configuration=config_json, publicly_available=form.publicly_available.data, public_identifier=form.public_identifier.data, default_autoload=form.default_autoload.data) else: rlms_obj = self.session.query(RLMS).filter_by( id=edit_id).first() rlms_obj.url = form.url.data rlms_obj.location = form.location.data rlms_obj.name = form.name.data rlms_obj.default_autoload = form.default_autoload.data rlms_obj.publicly_available = form.publicly_available.data rlms_obj.public_identifier = form.public_identifier.data rlms_obj.configuration = config_json self.session.add(rlms_obj) try: self.session.commit() except: self.session.rollback() raise if add_or_edit: rlms_id = rlms_obj.id else: rlms_id = edit_id labs_url = url_for('.labs', id=rlms_id, _external=True) if rlms == http_plugin.PLUGIN_NAME: if add_or_edit: # First, store the rlms identifier in the database in the context_id configuration['context_id'] = rlms_id config_json = json.dumps(configuration) rlms_obj.configuration = config_json try: self.session.commit() except: self.session.rollback() raise # Then, re-create the manager class and call setup rlms_instance = ManagerClass(config_json) try: setup_url = rlms_instance.setup(back_url=labs_url) except Exception as e: flash( gettext( "Couldn't load the setup URL! (this usually means that the plug-in is not correctly configured). Error message: %s" % e)) return redirect(url_for('.edit_view', id=rlms_id)) else: return redirect(setup_url) return redirect(labs_url) if not add_or_edit and rlms == http_plugin.PLUGIN_NAME: setup_url = url_for('.plugin_setup', rlms_id=edit_id) else: setup_url = None return self.render('labmanager_admin/create-rlms-step-2.html', name=rlms, version=version, form=form, fields=form.get_field_names(), error_messages=error_messages, edit_id=edit_id, setup_url=setup_url)
def requests(): """SCORM packages will perform requests to this method, which will interact with the permitted laboratories""" if request.method == 'GET': return render_template("test_requests.html") json_data = get_json() if json_data is None: return "Could not process JSON data" courses = json_data['courses'] request_payload_str = json_data['request-payload'] general_role = json_data.get('is-admin', False) author = json_data['user-id'] complete_name = json_data['full-name'] user_agent = json_data.get('user-agent', 'unknown user agent') origin_ip = json_data.get('origin-ip', 'unknown IP address') referer = json_data.get('referer', 'unknown referer') try: request_payload = json.loads(request_payload_str) except: traceback.print_exc() return "error: the request payload is not a valid JSON request" try: action = request_payload['action'] if action == 'reserve': experiment_identifier = request_payload['experiment'] else: # TODO: other operations: for teachers, etc. return "Unsupported operation" except KeyError: traceback.print_exc() return "Invalid response" # reserving... db_lms = db_session.query(LMS).filter_by(lms_login = g.lms).first() permission_on_lab = db_session.query(PermissionOnLaboratory).filter_by(lms_id = db_lms.id, local_identifier = experiment_identifier).first() good_msg = "No good news :-(" error_msg = None if permission_on_lab is None: error_msg = "Your LMS does not have permission to use that laboratory or that identifier does not exist" else: courses_configurations = [] for course_permission in permission_on_lab.course_permissions: if course_permission.course.course_id in courses: # Let the server choose among the best possible configuration courses_configurations.append(course_permission.configuration) if len(courses_configurations) == 0 and not general_role: error_msg = "Your LMS has permission to use that laboratory; but you are not enrolled in any course with permissions to use it" else: lms_configuration = permission_on_lab.configuration db_laboratory = permission_on_lab.laboratory db_rlms = db_laboratory.rlms db_rlms_version = db_rlms.rlms_version db_rlms_type = db_rlms_version.rlms_type ManagerClass = get_manager_class(db_rlms_type.name, db_rlms_version.version) remote_laboratory = ManagerClass(db_rlms.configuration) reservation_url = remote_laboratory.reserve(db_laboratory.laboratory_id, author, lms_configuration, courses_configurations, request_payload, user_agent, origin_ip, referer) good_msg = "You have been assigned %s of type %s version %s! <br/> Try it at <a href='%s'>%s</a>" % (db_rlms.name, db_rlms_type.name, db_rlms_version.version, reservation_url, reservation_url) if app.config.get('DEBUGGING_REQUESTS', True): courses_code = "<table><thead><tr><th>Course ID</th><th>Role</th></tr></thead><tbody>\n" for course_id in courses: role_in_course = courses[course_id] courses_code += "<tr><td>%s</td><td>%s</td></tr>\n" % (course_id, role_in_course) courses_code += "</tbody></table>" return """Hi %(name)s (username %(author)s), <p>I know that you're an admin ( %(admin)s ) in the LMS %(lms)s, and that you are in the following courses:</p> <br/> %(course_code)s <br/> <p>The following error messages were sent: %(error_msg)s</p> <p>The following good messages were sent: %(good_msg)s</p> Furthermore, you sent me this request: <pre> %(request)s </pre> And I'll process it! Original request: <pre> %(json)s </pre> """ % { 'name' : cgi.escape(complete_name), 'author' : cgi.escape(author), 'lms' : cgi.escape(g.lms), 'course_code' : courses_code, 'request' : cgi.escape(request_payload_str), 'admin' : general_role, 'json' : cgi.escape(json.dumps(json_data)), 'error_msg' : cgi.escape(error_msg or 'no error message'), 'good_msg' : good_msg or 'no good message', } else: if error_msg is None: return reservation_url else: return 'error:%s' % error_msg
def requests(): """SCORM packages will perform requests to this method, which will interact with the permitted laboratories""" db_lt = db.session.query(LearningTool).filter_by(name=g.lt).first() if request.method == 'GET': local_identifiers = [ permission.local_identifier for permission in db_lt.lab_permissions ] return render_template("http/requests.html", local_identifiers=local_identifiers, remote_addr=remote_addr(), courses=db_lt.courses) from labmanager.views import get_json json_data = get_json() if json_data is None: return messages_codes["ERROR_json"] courses = json_data['courses'] request_payload_str = json_data['request-payload'] general_role = json_data.get('is-admin', False) author = json_data['user-id'] complete_name = json_data['full-name'] user_agent = json_data.get('user-agent', 'unknown user agent') origin_ip = json_data.get('origin-ip', 'unknown IP address') referer = json_data.get('referer', 'unknown referer') try: request_payload = json.loads(request_payload_str) except: traceback.print_exc() return messages_codes["ERROR_invalid_json"] try: action = request_payload['action'] if action == 'reserve': experiment_identifier = request_payload['experiment'] else: # TODO: other operations: for instructors, booking, etc. return messages_codes["ERROR_unsupported"] except KeyError: traceback.print_exc() return messages_codes["ERROR_invalid"] # reserving... permission_to_lt = db.session.query(PermissionToLt).filter_by( lt=db_lt, local_identifier=experiment_identifier).first() good_msg = messages_codes["ERROR_no_good"] error_msg = None reservation_url = "" if permission_to_lt is None: error_msg = messages_codes["ERROR_permission"] else: courses_configurations = [] for course_permission in permission_to_lt.course_permissions: if course_permission.course.context_id in courses: # Let the server choose among the best possible configuration courses_configurations.append(course_permission.configuration) if len(courses_configurations) == 0 and not general_role: error_msg = messages_codes["ERROR_enrolled"] else: lt_configuration = permission_to_lt.configuration db_laboratory = permission_to_lt.laboratory db_rlms = db_laboratory.rlms rlms_version = db_rlms.version rlms_kind = db_rlms.kind # # Load the plug-in for the current RLMS, and instanciate it ManagerClass = get_manager_class(rlms_kind, rlms_version, db_rlms.id) remote_laboratory = ManagerClass(db_rlms.configuration) response = remote_laboratory.reserve( laboratory_id=db_laboratory.laboratory_id, username=author, institution=db_lt.name, general_configuration_str=lt_configuration, particular_configurations=courses_configurations, request_payload=request_payload, user_properties={ 'user_agent': user_agent, 'from_ip': origin_ip, 'referer': referer, }) reservation_url = response['load_url'] good_msg = messages_codes['MSG_asigned'] % ( db_rlms.kind, db_rlms.version, db_rlms.url, reservation_url, reservation_url) if app.config.get('DEBUGGING_REQUESTS', False): rendering_data = { 'name': cgi.escape(complete_name), 'author': cgi.escape(author), 'lms': cgi.escape(g.lt), 'courses': courses, 'request': cgi.escape(request_payload_str), 'admin': general_role, 'json': cgi.escape(json.dumps(json_data)), 'error_msg': cgi.escape(error_msg or 'no error message'), 'good_msg': good_msg or 'no good message', } return render_template('debug.html', data=rendering_data) if error_msg: return error_msg return reservation_url
def get_rlms(self): rlms_class = get_manager_class(self.kind, self.version, self.id) return rlms_class(self.configuration)
def _reserve_json(lab_name, public_rlms = False, public_lab = False, institution_id = None, rlms_identifier = None, gadget_url_base = None): # TODO XXX SECURITY BUG: THIS METHOD DOES NOT USE THE BOOKING THING st = request.args.get('st') or '' SHINDIG.url = 'http://shindig2.epfl.ch' if public_rlms: db_rlms = db.session.query(RLMS).filter_by(publicly_available = True, public_identifier = rlms_identifier).first() if db_rlms is None: return jsonify(success=False, message = gettext("That lab does not exist or it is not publicly available.")) lab_identifier = lab_name ple_configuration = '{}' institution_name = 'public-labs' # TODO: make sure that this name is unique courses_configurations = [] booking_required = False else: if public_lab: db_laboratory = db.session.query(Laboratory).filter_by(publicly_available = True, public_identifier = lab_name).first() if db_laboratory is None: return jsonify(success=False, message = gettext("That lab does not exist or it is not publicly available.")) ple_configuration = '{}' institution_name = 'public-labs' # TODO: make sure that this name is unique courses_configurations = [] else: institution = db.session.query(LearningTool).filter_by(name = institution_id).first() if institution is None or len(institution.shindig_credentials) < 1: return jsonify(success=False, message = gettext("This is not a valid PLE. Make sure that the institution id is fine and that there are Shindig Credentials configured")) SHINDIG.url = institution.shindig_credentials[0].shindig_url # Obtain current application data (especially, on which space is the user running it) current_app_str = urllib2.urlopen(url_shindig('/rest/apps/@self?st=%s' % st)).read() current_app_data = json.loads(current_app_str) space_id = current_app_data['entry'].get('parentId') or 'null parent' parent_type = current_app_data['entry'].get('parentType') if parent_type != '@space': return jsonify(success=False, message=gettext("Invalid parent: it should be a space, and it is a %(parenttype)s", parenttype=parent_type)) # Obtain the list of parent spaces of that space spaces = [space_id] get_parent_spaces(space_id, spaces) # Now, check permissions: # First, check if the lab is public (e.g. the lab can be accessed by anyone) # Second, check accesibility permissions (e.g. the lab is accessible for everyone from that institution without specifying any Graasp space). # After that, in the case that there are not accesibility permissions, check for that institution if there is a permission identified by that lab_name, and check which courses (spaces in OpenSocial) have that permission. public_lab_db = db.session.query(Laboratory).filter_by(public_identifier = lab_name, publicly_available = True).first() courses_configurations = [] if public_lab_db is None: # No public access is granted for the lab, check accesibility permissions accessible_permission = db.session.query(PermissionToLt).filter_by(lt = institution, local_identifier = lab_name, accessible = True).first() if accessible_permission is None: permission = db.session.query(PermissionToLt).filter_by(lt = institution, local_identifier = lab_name).first() if permission is None: return jsonify(success=False, message=gettext("Your PLE is valid, but don't have permissions for the requested laboratory.")) for course_permission in permission.course_permissions: if course_permission.course.context_id in spaces: # Let the server choose among the best possible configuration courses_configurations.append(course_permission.configuration) if len(courses_configurations) == 0: return jsonify(success=False, message = gettext("Your PLE is valid and your lab too, but you're not in one of the spaces that have permissions (you are in %(space)r)", space=spaces)) else: # There is a accesibility permission for that lab and institution permission = accessible_permission ple_configuration = permission.configuration db_laboratory = permission.laboratory institution_name = institution.name else: # There is a public permission for the lab ple_configuration = [] db_laboratory = public_lab_db institution_name = institution.name lab_identifier = db_laboratory.laboratory_id db_rlms = db_laboratory.rlms # Obtain user data if st == 'null' and (public_lab or public_rlms): user_id = 'no-id' else: try: current_user_str = urllib2.urlopen(url_shindig("/rest/people/@me/@self?st=%s" % st)).read() current_user_data = json.loads(current_user_str) except: traceback.print_exc() if public_lab or public_rlms: user_id = 'no-id' else: return jsonify(success=False, message=gettext("Could not connect to %(urlshindig)s.", urlshindig=url_shindig("/rest/people/@me/@self?st=%s" % st))) else: # name = current_user_data['entry'].get('displayName') or 'anonymous' user_id = current_user_data['entry'].get('id') or 'no-id' rlms_version = db_rlms.version rlms_kind = db_rlms.kind user_agent = unicode(request.user_agent) origin_ip = remote_addr() referer = request.referrer # Load the plug-in for the current RLMS, and instanciate it ManagerClass = get_manager_class(rlms_kind, rlms_version, db_rlms.id) remote_laboratory = ManagerClass(db_rlms.configuration) kwargs = {} locale = request.args.get('locale') or None if locale: kwargs['locale'] = locale lab_config = request.args.get('lab_config') try: lab_config = urllib.unquote(lab_config) json.loads(lab_config) # Verify that it's a valid JSON except: lab_config = '{}' if lab_config: request_payload = { 'initial' : lab_config } else: request_payload = {} try: response = remote_laboratory.reserve(laboratory_id = lab_identifier, username = user_id, institution = institution_name, general_configuration_str = ple_configuration, particular_configurations = courses_configurations, request_payload = request_payload, user_properties = { 'user_agent' : user_agent, 'from_ip' : origin_ip, 'referer' : referer }, back = url_for('.reload', _external = True), **kwargs) except Exception as e: app.logger.error("Error processing request: %s" % e, exc_info = True) traceback.print_exc() # Don't translate, just in case there are issues with the problem itself return jsonify(success=False, message = "There was an error performing the reservation to the final laboratory.") if Capabilities.WIDGET in remote_laboratory.get_capabilities(): reservation_id = response['reservation_id'] else: reservation_id = response['load_url'] quoted_reservation_id = urllib2.quote(reservation_id, '') g4l_session_id = "{0}-{1}-{2}".format(quoted_reservation_id, time.time(), str(random.randint(0, 9999)).zfill(4)) return jsonify(success=True, reservation_id=quoted_reservation_id, g4l_session_id=g4l_session_id, shindig_url=SHINDIG.url)
def _extract_widget_config(rlms_db, laboratory_identifier, widget_name, lab_found): autoload = None if request.args.get('autoload'): autoload = request.args['autoload'].lower() == 'true' height = None if request.args.get('height'): try: height = '%spx' % int(request.args['height']) except: pass base_data = { 'translations' : {}, 'mails' : {} } if height is not None: base_data['height'] = height scale = None if request.args.get('scale'): try: scale = int(request.args['scale']) except: pass if scale is not None: base_data['scale'] = scale if not lab_found: return base_data if autoload is None and rlms_db.default_autoload is not None: autoload = rlms_db.default_autoload RLMS_CLASS = get_manager_class(rlms_db.kind, rlms_db.version, rlms_db.id) rlms = RLMS_CLASS(rlms_db.configuration) try: capabilities = rlms.get_capabilities() except Exception as e: traceback.print_exc() raise Exception("Error retrieving capabilities: %s" % e) if Capabilities.FORCE_SEARCH in capabilities: if autoload is None: autoload = True # By default in those cases where a search is mandatory else: # labs = [ lab for lab in rlms.get_laboratories() if lab.laboratory_id == laboratory_identifier ] # if not labs: # # The laboratory has changed # return None # # if autoload is None: # autoload = labs[0].autoload pass default_height = rlms.get_default_height() if default_height and not base_data.get('height'): base_data['height'] = '{}px'.format(default_height) height = base_data['height'] default_scale = rlms.get_default_scale() if default_scale and not base_data.get('scale'): base_data['scale'] = int(default_scale) scale = base_data['scale'] if Capabilities.TRANSLATIONS in capabilities: translations = rlms.get_translations(laboratory_identifier) if 'translations' not in translations: translations['translations'] = {} if 'mails' not in translations: translations['mails'] = [] else: translations = {'translations' : {}, 'mails' : []} # Only if no translation is regularly provided and translation_list is supoprted if Capabilities.TRANSLATION_LIST in capabilities: translation_list = list((rlms.get_translation_list(laboratory_identifier) or {}).get('supported_languages', [])) for lang in translations['translations']: if lang not in translation_list: translation_list.append(lang) else: translation_list = [] if Capabilities.CHECK_URLS in capabilities: check_urls = rlms.get_check_urls(laboratory_identifier) else: check_urls = [] if autoload and len(translations['translations']) == 0: show_languages = False else: show_languages = True show_empty_languages = len(translation_list) > 0 if Capabilities.WIDGET in capabilities: widgets = rlms.list_widgets(laboratory_identifier) for widget in widgets: if widget['name'] == widget_name: widget['autoload'] = autoload widget['translations'] = translations widget['translation_list'] = translation_list widget['show_languages'] = show_languages widget['show_empty_languages'] = show_empty_languages if check_urls: widget['check_urls'] = check_urls if height is not None: widget['height'] = height if scale is not None: widget['scale'] = scale return widget base_data['autoload'] = autoload base_data['translations'] = translations base_data['translation_list'] = translation_list base_data['show_languages'] = show_languages base_data['show_empty_languages'] = show_empty_languages if check_urls: base_data['check_urls'] = check_urls return base_data
def _reserve_impl(lab_name, public_rlms=False, public_lab=False, institution_id=None, rlms_identifier=None, gadget_url_base=None): # TODO XXX SECURITY BUG: THIS METHOD DOES NOT USE THE BOOKING THING st = request.args.get('st') or '' SHINDIG.url = 'http://shindig2.epfl.ch' if public_rlms: db_rlms = db.session.query(RLMS).filter_by( publicly_available=True, public_identifier=rlms_identifier).first() if db_rlms is None: return render_template( "opensocial/errors.html", message=gettext( "That lab does not exist or it is not publicly available.") ) lab_identifier = lab_name ple_configuration = '{}' institution_name = 'public-labs' # TODO: make sure that this name is unique courses_configurations = [] booking_required = False else: if public_lab: db_laboratory = db.session.query(Laboratory).filter_by( publicly_available=True, public_identifier=lab_name).first() if db_laboratory is None: return render_template( "opensocial/errors.html", message=gettext( "That lab does not exist or it is not publicly available." )) ple_configuration = '{}' institution_name = 'public-labs' # TODO: make sure that this name is unique courses_configurations = [] else: institution = db.session.query(LearningTool).filter_by( name=institution_id).first() if institution is None or len(institution.shindig_credentials) < 1: return render_template( "opensocial/errors.html", message=gettext( "This is not a valid PLE. Make sure that the institution id is fine and that there are Shindig Credentials configured" )) SHINDIG.url = institution.shindig_credentials[0].shindig_url # Obtain current application data (especially, on which space is the user running it) current_app_str = urllib2.urlopen( url_shindig('/rest/apps/@self?st=%s' % st)).read() current_app_data = json.loads(current_app_str) space_id = current_app_data['entry'].get( 'parentId') or 'null parent' parent_type = current_app_data['entry'].get('parentType') if parent_type != '@space': return render_template( "opensocial/errors.html", message=gettext( "Invalid parent: it should be a space, and it is a %(parenttype)s", parenttype=parent_type)) # Obtain the list of parent spaces of that space spaces = [space_id] get_parent_spaces(space_id, spaces) # Now, check permissions: # First, check if the lab is public (e.g. the lab can be accessed by anyone) # Second, check accesibility permissions (e.g. the lab is accessible for everyone from that institution without specifying any Graasp space). # After that, in the case that there are not accesibility permissions, check for that institution if there is a permission identified by that lab_name, and check which courses (spaces in OpenSocial) have that permission. public_lab_db = db.session.query(Laboratory).filter_by( public_identifier=lab_name, publicly_available=True).first() courses_configurations = [] if public_lab_db is None: # No public access is granted for the lab, check accesibility permissions accessible_permission = db.session.query( PermissionToLt).filter_by(lt=institution, local_identifier=lab_name, accessible=True).first() if accessible_permission is None: permission = db.session.query(PermissionToLt).filter_by( lt=institution, local_identifier=lab_name).first() if permission is None: return render_template( "opensocial/errors.html", message=gettext( "Your PLE is valid, but don't have permissions for the requested laboratory." )) for course_permission in permission.course_permissions: if course_permission.course.context_id in spaces: # Let the server choose among the best possible configuration courses_configurations.append( course_permission.configuration) if len(courses_configurations) == 0: return render_template( "opensocial/errors.html", message=gettext( "Your PLE is valid and your lab too, but you're not in one of the spaces that have permissions (you are in %(space)r)", space=spaces)) else: # There is a accesibility permission for that lab and institution permission = accessible_permission ple_configuration = permission.configuration db_laboratory = permission.laboratory institution_name = institution.name else: # There is a public permission for the lab ple_configuration = [] db_laboratory = public_lab_db institution_name = institution.name booking_required = db_laboratory.go_lab_reservation lab_identifier = db_laboratory.laboratory_id db_rlms = db_laboratory.rlms if booking_required: next_session = check_ils_booking(gadget_url_base) if next_session is not None: return render_template("opensocial/errors-booking.html", next_session=next_session) # Obtain user data if st == 'null' and (public_lab or public_rlms): user_id = 'no-id' else: try: current_user_str = urllib2.urlopen( url_shindig("/rest/people/@me/@self?st=%s" % st)).read() current_user_data = json.loads(current_user_str) except: traceback.print_exc() if public_lab or public_rlms: user_id = 'no-id' else: return render_template( "opensocial/errors.html", message=gettext("Could not connect to %(urlshindig)s.", urlshindig=url_shindig( "/rest/people/@me/@self?st=%s" % st))) else: # name = current_user_data['entry'].get('displayName') or 'anonymous' user_id = current_user_data['entry'].get('id') or 'no-id' rlms_version = db_rlms.version rlms_kind = db_rlms.kind user_agent = unicode(request.user_agent) origin_ip = remote_addr() referer = request.referrer # Load the plug-in for the current RLMS, and instanciate it ManagerClass = get_manager_class(rlms_kind, rlms_version, db_rlms.id) remote_laboratory = ManagerClass(db_rlms.configuration) kwargs = {} locale = request.args.get('locale') or None if locale: kwargs['locale'] = locale lab_config = request.args.get('lab_config') try: lab_config = urllib.unquote(lab_config) json.loads(lab_config) # Verify that it's a valid JSON except: lab_config = '{}' if lab_config: request_payload = {'initial': lab_config} else: request_payload = {} try: response = remote_laboratory.reserve( laboratory_id=lab_identifier, username=user_id, institution=institution_name, general_configuration_str=ple_configuration, particular_configurations=courses_configurations, request_payload=request_payload, user_properties={ 'user_agent': user_agent, 'from_ip': origin_ip, 'referer': referer }, back=url_for('.reload', _external=True), **kwargs) except Exception as e: app.logger.error("Error processing request: %s" % e, exc_info=True) traceback.print_exc() # Don't translate, just in case there are issues with the problem itself return render_template( "opensocial/errors.html", message= "There was an error performing the reservation to the final laboratory." ) else: if Capabilities.WIDGET in remote_laboratory.get_capabilities(): reservation_id = response['reservation_id'] else: reservation_id = response['load_url'] quoted_reservation_id = urllib2.quote(reservation_id, '') g4l_session_id = "{0}-{1}-{2}".format( quoted_reservation_id, time.time(), str(random.randint(0, 9999)).zfill(4)) return render_template("opensocial/confirmed.html", reservation_id=quoted_reservation_id, g4l_session_id=g4l_session_id, shindig_url=SHINDIG.url)
def labs(self, id): # # TODO: CSRF is not used here. Security hole # rlms_db = self.session.query(RLMS).filter_by(id=id).first() if rlms_db is None: return abort(404) query = request.args.get('q') if query is not None: page = request.args.get('p', '1') try: page = int(page) except: page = 1 else: page = 1 RLMS_CLASS = get_manager_class(rlms_db.kind, rlms_db.version, rlms_db.id) rlms = RLMS_CLASS(rlms_db.configuration) if query: query_results = rlms.search(query=query, page=page) labs = query_results['laboratories'] force_search = False number_of_pages = query_results.get('pages', 1) pages = [] if number_of_pages > 1: for p in xrange(1, number_of_pages + 1): obj = { 'label': unicode(p), 'link': url_for('.labs', id=id, q=query, p=p) } obj['active'] = (p != page) pages.append(obj) else: query_results = {} labs = rlms.get_laboratories() capabilities = rlms.get_capabilities() force_search = Capabilities.FORCE_SEARCH in capabilities pages = [] registered_labs = [lab.laboratory_id for lab in rlms_db.laboratories] if request.method == 'POST': selected = [] for name, value in request.form.items(): if name != 'action' and value == 'on': for lab in labs: if lab.laboratory_id == name: selected.append(lab) changes = False if request.form['action'] == 'register': for lab in selected: if not lab.laboratory_id in registered_labs: self.session.add( Laboratory(name=lab.name, laboratory_id=lab.laboratory_id, rlms=rlms_db)) changes = True elif request.form['action'] == 'unregister': for lab in selected: if lab.laboratory_id in registered_labs: cur_lab_db = None for lab_db in rlms_db.laboratories: if lab_db.laboratory_id == lab.laboratory_id: cur_lab_db = lab_db break if cur_lab_db is not None: self.session.delete(cur_lab_db) changes = True if changes: self.session.commit() registered_labs = [lab.laboratory_id for lab in rlms_db.laboratories] return self.render('labmanager_admin/lab-list.html', rlms=rlms_db, labs=labs, registered_labs=registered_labs, query=query, force_search=force_search, pages=pages, page=page, id=id)
def requests(): """SCORM packages will perform requests to this method, which will interact with the permitted laboratories""" db_lt = db.session.query(LearningTool).filter_by(name = g.lt).first() if request.method == 'GET': local_identifiers = [ permission.local_identifier for permission in db_lt.lab_permissions ] return render_template("http/requests.html", local_identifiers = local_identifiers, remote_addr = remote_addr(), courses = db_lt.courses) from labmanager.views import get_json json_data = get_json() if json_data is None: return messages_codes["ERROR_json"] courses = json_data['courses'] request_payload_str = json_data['request-payload'] general_role = json_data.get('is-admin', False) author = json_data['user-id'] complete_name = json_data['full-name'] user_agent = json_data.get('user-agent', 'unknown user agent') origin_ip = json_data.get('origin-ip', 'unknown IP address') referer = json_data.get('referer', 'unknown referer') try: request_payload = json.loads(request_payload_str) except: traceback.print_exc() return messages_codes["ERROR_invalid_json"] try: action = request_payload['action'] if action == 'reserve': experiment_identifier = request_payload['experiment'] else: # TODO: other operations: for instructors, booking, etc. return messages_codes["ERROR_unsupported"] except KeyError: traceback.print_exc() return messages_codes["ERROR_invalid"] # reserving... permission_to_lt = db.session.query(PermissionToLt).filter_by(lt = db_lt, local_identifier = experiment_identifier).first() good_msg = messages_codes["ERROR_no_good"] error_msg = None reservation_url = "" if permission_to_lt is None: error_msg = messages_codes["ERROR_permission"] else: courses_configurations = [] for course_permission in permission_to_lt.course_permissions: if course_permission.course.context_id in courses: # Let the server choose among the best possible configuration courses_configurations.append(course_permission.configuration) if len(courses_configurations) == 0 and not general_role: error_msg = messages_codes["ERROR_enrolled"] else: lt_configuration = permission_to_lt.configuration db_laboratory = permission_to_lt.laboratory db_rlms = db_laboratory.rlms rlms_version = db_rlms.version rlms_kind = db_rlms.kind # # Load the plug-in for the current RLMS, and instanciate it ManagerClass = get_manager_class(rlms_kind, rlms_version, db_rlms.id) remote_laboratory = ManagerClass(db_rlms.configuration) response = remote_laboratory.reserve(laboratory_id = db_laboratory.laboratory_id, username = author, institution = db_lt.name, general_configuration_str = lt_configuration, particular_configurations = courses_configurations, request_payload = request_payload, user_properties = { 'user_agent' : user_agent, 'from_ip' : origin_ip, 'referer' : referer, }) reservation_url = response['load_url'] good_msg = messages_codes['MSG_asigned'] % (db_rlms.kind, db_rlms.version, db_rlms.url, reservation_url, reservation_url) if app.config.get('DEBUGGING_REQUESTS', False): rendering_data = { 'name' : cgi.escape(complete_name), 'author' : cgi.escape(author), 'lms' : cgi.escape(g.lt), 'courses' : courses, 'request' : cgi.escape(request_payload_str), 'admin' : general_role, 'json' : cgi.escape(json.dumps(json_data)), 'error_msg' : cgi.escape(error_msg or 'no error message'), 'good_msg' : good_msg or 'no good message', } return render_template('debug.html', data=rendering_data) if error_msg: return error_msg return reservation_url
def requests(): """SCORM packages will perform requests to this method, which will interact with the permitted laboratories""" if request.method == 'GET': return render_template("test_requests.html") json_data = get_json() if json_data is None: return "Could not process JSON data" courses = json_data['courses'] request_payload_str = json_data['request-payload'] general_role = json_data.get('is-admin', False) author = json_data['user-id'] complete_name = json_data['full-name'] user_agent = json_data.get('user-agent', 'unknown user agent') origin_ip = json_data.get('origin-ip', 'unknown IP address') referer = json_data.get('referer', 'unknown referer') try: request_payload = json.loads(request_payload_str) except: traceback.print_exc() return "error: the request payload is not a valid JSON request" try: action = request_payload['action'] if action == 'reserve': experiment_identifier = request_payload['experiment'] else: # TODO: other operations: for teachers, etc. return "Unsupported operation" except KeyError: traceback.print_exc() return "Invalid response" # reserving... db_lms = db_session.query(LMS).filter_by(lms_login=g.lms).first() permission_on_lab = db_session.query(PermissionOnLaboratory).filter_by( lms_id=db_lms.id, local_identifier=experiment_identifier).first() good_msg = "No good news :-(" error_msg = None if permission_on_lab is None: error_msg = "Your LMS does not have permission to use that laboratory or that identifier does not exist" else: courses_configurations = [] for course_permission in permission_on_lab.course_permissions: if course_permission.course.course_id in courses: # Let the server choose among the best possible configuration courses_configurations.append(course_permission.configuration) if len(courses_configurations) == 0 and not general_role: error_msg = "Your LMS has permission to use that laboratory; but you are not enrolled in any course with permissions to use it" else: lms_configuration = permission_on_lab.configuration db_laboratory = permission_on_lab.laboratory db_rlms = db_laboratory.rlms db_rlms_version = db_rlms.rlms_version db_rlms_type = db_rlms_version.rlms_type ManagerClass = get_manager_class(db_rlms_type.name, db_rlms_version.version) remote_laboratory = ManagerClass(db_rlms.configuration) reservation_url = remote_laboratory.reserve( db_laboratory.laboratory_id, author, lms_configuration, courses_configurations, user_agent, origin_ip, referer) good_msg = "You have been assigned %s of type %s version %s! <br/> Try it at <a href='%s'>%s</a>" % ( db_rlms.name, db_rlms_type.name, db_rlms_version.version, reservation_url, reservation_url) if app.config.get('DEBUGGING_REQUESTS', True): courses_code = "<table><thead><tr><th>Course ID</th><th>Role</th></tr></thead><tbody>\n" for course_id in courses: role_in_course = courses[course_id] courses_code += "<tr><td>%s</td><td>%s</td></tr>\n" % ( course_id, role_in_course) courses_code += "</tbody></table>" return """Hi %(name)s (username %(author)s), <p>I know that you're an admin ( %(admin)s ) in the LMS %(lms)s, and that you are in the following courses:</p> <br/> %(course_code)s <br/> <p>The following error messages were sent: %(error_msg)s</p> <p>The following good messages were sent: %(good_msg)s</p> Furthermore, you sent me this request: <pre> %(request)s </pre> And I'll process it! Original request: <pre> %(json)s </pre> """ % { 'name': cgi.escape(complete_name), 'author': cgi.escape(author), 'lms': cgi.escape(g.lms), 'course_code': courses_code, 'request': cgi.escape(request_payload_str), 'admin': general_role, 'json': cgi.escape(json.dumps(json_data)), 'error_msg': cgi.escape(error_msg or 'no error message'), 'good_msg': good_msg or 'no good message', } else: if error_msg is None: return reservation_url else: return 'error:%s' % error_msg
def labs(self, id): # # TODO: CSRF is not used here. Security hole # rlms_db = self.session.query(RLMS).filter_by(id = id).first() if rlms_db is None: return abort(404) query = request.args.get('q') if query is not None: page = request.args.get('p', '1') try: page = int(page) except: page = 1 else: page = 1 RLMS_CLASS = get_manager_class(rlms_db.kind, rlms_db.version, rlms_db.id) rlms = RLMS_CLASS(rlms_db.configuration) if query: query_results = rlms.search(query = query, page = page) labs = query_results['laboratories'] force_search = False number_of_pages = query_results.get('pages', 1) pages = [] if number_of_pages > 1: for p in xrange(1, number_of_pages + 1): obj = { 'label' : unicode(p), 'link' : url_for('.labs', id = id, q = query, p = p) } obj['active'] = (p != page) pages.append(obj) else: query_results = {} labs = rlms.get_laboratories() capabilities = rlms.get_capabilities() force_search = Capabilities.FORCE_SEARCH in capabilities pages = [] registered_labs = [ lab.laboratory_id for lab in rlms_db.laboratories ] if request.method == 'POST': selected = [] for name, value in request.form.items(): if name != 'action' and value == 'on': for lab in labs: if lab.laboratory_id == name: selected.append(lab) changes = False if request.form['action'] == 'register': for lab in selected: if not lab.laboratory_id in registered_labs: self.session.add(Laboratory(name = lab.name, laboratory_id = lab.laboratory_id, rlms = rlms_db)) changes = True elif request.form['action'] == 'unregister': for lab in selected: if lab.laboratory_id in registered_labs: cur_lab_db = None for lab_db in rlms_db.laboratories: if lab_db.laboratory_id == lab.laboratory_id: cur_lab_db = lab_db break if cur_lab_db is not None: self.session.delete(cur_lab_db) changes = True if changes: self.session.commit() registered_labs = [ lab.laboratory_id for lab in rlms_db.laboratories ] return self.render('labmanager_admin/lab-list.html', rlms = rlms_db, labs = labs, registered_labs = registered_labs, query = query, force_search = force_search, pages = pages, page = page, id = id)
def _add_or_edit(self, rlms, version, add_or_edit, obj, config): edit_id = request.args.get('id') form_class = get_form_class(rlms, version) form = form_class(add_or_edit=add_or_edit, obj = obj) error_messages = [] if form.validate_on_submit(): configuration = config for key in form.get_field_names(): if key not in dir(forms.AddForm): field = getattr(form, key) is_password = '******' in unicode(field.type).lower() # If we're editing, and this field is a password, do not change it if is_password and not add_or_edit and field.data == '': continue configuration[key] = field.data config_json = json.dumps(configuration) current_rlms_id = None if add_or_edit else edit_id ManagerClass = get_manager_class(rlms, version, current_rlms_id) rlms_instance = ManagerClass(config_json) if hasattr(rlms_instance, 'test'): try: error_messages = rlms_instance.test() or [] except Exception as e: error_messages.append(u'%s%s' % (gettext("Error testing the RLMS:"), e)) traceback.print_exc() if form.publicly_available.data and len(form.public_identifier.data) == 0: form.public_identifier.errors = [gettext("If the RLMS is public, it must have a public identifier")] error_messages.append(gettext("Invalid public identifier")) elif form.publicly_available.data and len(form.public_identifier.data) < 4: form.public_identifier.errors = [gettext("If the RLMS is public, it must have a public identifier with at least 4 characters")] error_messages.append(gettext("Invalid public identifier")) elif form.publicly_available.data: # If publicly available, retrieve existing RLMS with that public identifier existing_objects = self.session.query(RLMS).filter_by(public_identifier = form.public_identifier.data).all() if not add_or_edit: # If editing, don't count the one being edited existing_objects = [ existing_obj for existing_obj in existing_objects if unicode(existing_obj.id) != unicode(edit_id)] if existing_objects: form.public_identifier.errors = [gettext("That identifier is already taken")] error_messages.append(gettext("Use other identifier or don't make the RLMS public")) if not error_messages: if add_or_edit: rlms_obj = RLMS(kind = rlms, version = version, name = form.name.data, url = form.url.data, location = form.location.data, configuration = config_json, publicly_available = form.publicly_available.data, public_identifier = form.public_identifier.data, default_autoload = form.default_autoload.data) else: rlms_obj = self.session.query(RLMS).filter_by(id = edit_id).first() rlms_obj.url = form.url.data rlms_obj.location = form.location.data rlms_obj.name = form.name.data rlms_obj.default_autoload = form.default_autoload.data rlms_obj.publicly_available = form.publicly_available.data rlms_obj.public_identifier = form.public_identifier.data rlms_obj.configuration = config_json self.session.add(rlms_obj) try: self.session.commit() except: self.session.rollback() raise if add_or_edit: rlms_id = rlms_obj.id else: rlms_id = edit_id labs_url = url_for('.labs', id = rlms_id, _external = True) if rlms == http_plugin.PLUGIN_NAME: if add_or_edit: # First, store the rlms identifier in the database in the context_id configuration['context_id'] = rlms_id config_json = json.dumps(configuration) rlms_obj.configuration = config_json try: self.session.commit() except: self.session.rollback() raise # Then, re-create the manager class and call setup rlms_instance = ManagerClass(config_json) try: setup_url = rlms_instance.setup(back_url = labs_url) except Exception as e: flash(gettext("Couldn't load the setup URL! (this usually means that the plug-in is not correctly configured). Error message: %s" % e)) return redirect(url_for('.edit_view', id = rlms_id)) else: return redirect(setup_url) return redirect(labs_url) if not add_or_edit and rlms == http_plugin.PLUGIN_NAME: setup_url = url_for('.plugin_setup', rlms_id = edit_id) else: setup_url = None return self.render('labmanager_admin/create-rlms-step-2.html', name = rlms, version = version, form = form, fields = form.get_field_names(), error_messages = error_messages, edit_id = edit_id, setup_url = setup_url)
def extract_labs(rlms, single_lab=None, fmt='json', age_ranges=None, domains=None): if fmt == 'xml': lab_formatter = lab_to_xml else: lab_formatter = lab_to_json RLMS_CLASS = get_manager_class(rlms.kind, rlms.version, rlms.id) rlms_inst = RLMS_CLASS(rlms.configuration) labs = rlms_inst.get_laboratories() public_laboratories = [] for lab in labs: if single_lab is not None and lab.laboratory_id != single_lab: # If filtering, remove those labs continue if Capabilities.WIDGET in rlms_inst.get_capabilities(): widgets = rlms_inst.list_widgets(lab.laboratory_id) else: widgets = [{ 'name': lab.name or 'default', 'description': lab.description }] lab_widgets = [] for widget in widgets: if single_lab is None: link = url_for('opensocial.public_rlms_widget_xml', rlms_identifier=rlms.public_identifier, lab_name=lab.laboratory_id, widget_name=widget['name'], _external=True) if link.startswith('https://'): link = link.replace('https://', 'http://', 1) external_url = url_for('repository.preview_public_rlms', rlms_id=rlms.public_identifier, widget_name=widget['name'], lab_name=lab.laboratory_id, _external=True) else: link = url_for('opensocial.public_widget_xml', lab_name=lab.public_identifier, widget_name=widget['name'], _external=True) if link.startswith('https://'): link = link.replace('https://', 'http://', 1) external_url = url_for('repository.preview_public_lab', widget_name=widget['name'], public_identifier=lab.public_identifier, _external=True) lab_widgets.append({ 'name': widget['name'], 'description': widget['description'], 'link': link, 'external': external_url, }) public_laboratories.append( lab_formatter(lab, lab_widgets, rlms, single_lab is not None, age_ranges, domains)) return public_laboratories
def _extract_widget_config(rlms_db, laboratory_identifier, widget_name, lab_found): autoload = None if request.args.get('autoload'): autoload = request.args['autoload'].lower() == 'true' height = None if request.args.get('height'): try: height = '%spx' % int(request.args['height']) except: pass base_data = {'translations': {}, 'mails': {}} if height is not None: base_data['height'] = height scale = None if request.args.get('scale'): try: scale = int(request.args['scale']) except: pass if scale is not None: base_data['scale'] = scale if not lab_found: return base_data if autoload is None and rlms_db.default_autoload is not None: autoload = rlms_db.default_autoload RLMS_CLASS = get_manager_class(rlms_db.kind, rlms_db.version, rlms_db.id) rlms = RLMS_CLASS(rlms_db.configuration) try: capabilities = rlms.get_capabilities() except Exception as e: traceback.print_exc() raise Exception("Error retrieving capabilities: %s" % e) if Capabilities.FORCE_SEARCH in capabilities: if autoload is None: autoload = True # By default in those cases where a search is mandatory else: # labs = [ lab for lab in rlms.get_laboratories() if lab.laboratory_id == laboratory_identifier ] # if not labs: # # The laboratory has changed # return None # # if autoload is None: # autoload = labs[0].autoload pass if Capabilities.TRANSLATIONS in capabilities: translations = rlms.get_translations(laboratory_identifier) if 'translations' not in translations: translations['translations'] = {} if 'mails' not in translations: translations['mails'] = [] else: translations = {'translations': {}, 'mails': []} # Only if no translation is regularly provided and translation_list is supoprted if len(translations['translations'] ) == 0 and Capabilities.TRANSLATION_LIST in capabilities: translation_list = list( (rlms.get_translation_list(laboratory_identifier) or {}).get('supported_languages', [])) else: translation_list = [] if autoload and len(translations['translations']) == 0: show_languages = False else: show_languages = True show_empty_languages = len(translation_list) > 0 if Capabilities.WIDGET in capabilities: widgets = rlms.list_widgets(laboratory_identifier) for widget in widgets: if widget['name'] == widget_name: widget['autoload'] = autoload widget['translations'] = translations widget['translation_list'] = translation_list widget['show_languages'] = show_languages widget['show_empty_languages'] = show_empty_languages if height is not None: widget['height'] = height if scale is not None: widget['scale'] = scale return widget base_data['autoload'] = autoload base_data['translations'] = translations base_data['translation_list'] = translation_list base_data['show_languages'] = show_languages base_data['show_empty_languages'] = show_empty_languages return base_data