def android_client_get_ics(resource_type, identifier, semester): """ android client get a student or teacher's ics file If the student does not have privacy mode, anyone can use student number to subscribe his calendar. If the privacy mode is on and there is no HTTP basic authentication, return a 401(unauthorized) status code and the Android client ask user for password to try again. """ from flask import redirect, url_for, request from everyclass.server.db.dao import PrivacySettings, CalendarToken, User from everyclass.server.rpc.api_server import APIServer from everyclass.server.utils.resource_identifier_encrypt import decrypt # 检查 URL 参数 try: res_type, res_id = decrypt(identifier) except ValueError: return "Invalid identifier", 400 if resource_type not in ('student', 'teacher') or resource_type != res_type: return "Unknown resource type", 400 if resource_type == 'teacher': try: teacher = APIServer.get_teacher_timetable(res_id, semester) except Exception as e: return handle_exception_with_error_page(e) cal_token = CalendarToken.get_or_set_calendar_token( resource_type=resource_type, identifier=teacher.teacher_id, semester=semester) return redirect( url_for('calendar.ics_download', calendar_token=cal_token)) else: # student try: student = APIServer.get_student_timetable(res_id, semester) except Exception as e: return handle_exception_with_error_page(e) with elasticapm.capture_span('get_privacy_settings'): privacy_level = PrivacySettings.get_level(student.student_id) # get authorization from HTTP header and verify password if privacy is on if privacy_level != 0: if not request.authorization: return "Unauthorized (privacy on)", 401 username, password = request.authorization if not User.check_password(username, password): return "Unauthorized (password wrong)", 401 if student.student_id != username: return "Unauthorized (username mismatch)", 401 cal_token = CalendarToken.get_or_set_calendar_token( resource_type=resource_type, identifier=student.student_id, semester=semester) return redirect( url_for('calendar.ics_download', calendar_token=cal_token))
def login(): """ 登录页 判断学生是否未注册,若已经注册,渲染登录页。否则跳转到注册页面。 """ if request.method == 'GET': if session.get(SESSION_LAST_VIEWED_STUDENT, None): user_name = session[SESSION_LAST_VIEWED_STUDENT].name else: user_name = None return render_template('user/login.html', name=user_name) else: # 表单提交 if not request.form.get("password", None): flash(MSG_EMPTY_PASSWORD) return redirect(url_for("user.login")) # captcha if not TencentCaptcha.verify_old(): flash(MSG_INVALID_CAPTCHA) return redirect(url_for("user.login")) if request.form.get("xh", None): # 已手动填写用户名 student_id = request.form["xh"] # 检查学号是否存在 try: Entity.get_student(student_id) except RpcResourceNotFound: flash(MSG_USERNAME_NOT_EXIST) return redirect(url_for("user.login")) except Exception as e: return handle_exception_with_error_page(e) else: if session.get(SESSION_LAST_VIEWED_STUDENT, None): student_id = session[ SESSION_LAST_VIEWED_STUDENT].sid_orig # 没有手动填写,使用获取最后浏览的学生 else: flash(MSG_EMPTY_USERNAME) # 没有最后浏览的学生,必须填写用户名 return redirect(url_for("user.login")) try: success = User.check_password(student_id, request.form["password"]) except ValueError: # 未注册 flash(MSG_NOT_REGISTERED) _session_save_student_to_register_(student_id) return redirect(url_for("user.register")) if success: try: student = Entity.get_student(student_id) except Exception as e: return handle_exception_with_error_page(e) # 登录态写入 session session[SESSION_CURRENT_USER] = StudentSession( sid_orig=student_id, sid=student.student_id_encoded, name=student.name) return redirect(url_for("user.main")) else: flash(MSG_WRONG_PASSWORD) return redirect(url_for("user.login"))