Пример #1
0
 def get(self):
     values = {"page_title": self.page_title()}
     values['courses'] = COURSE_LIST
     user = users.get_current_user()
     if user:
         rosebotics_student = RoseboticsStudent.get_by_id(
             user.email().lower())
         if rosebotics_student is None:
             rosebotics_student = RoseboticsStudent(id=user.email().lower())
             rosebotics_student.put()
         values["logout_url"] = users.create_logout_url("/")
         values["rosebotics_student"] = rosebotics_student
         most_recent_course = recent_track_utils.get_most_recent_course(
             rosebotics_student.key)
         if most_recent_course is not None:
             values["most_recent_track"] = most_recent_course
         values.update(
             recent_track_utils.get_recent_tracks(rosebotics_student.key))
     elif self.requires_oauth():
         self.redirect("/courses")
         return
     else:
         values["login_url"] = users.create_login_url("/courses")
     self.update_values(user, values)
     template = jinja_env.get_template(self.template_file())
     self.response.out.write(template.render(values))
Пример #2
0
    def personalize_page_and_get_user(self):
        """If the user exists, add personalized fields to the navbar."""
        user = self.get_user()
        PageInitializerService.get().initialize(self.template_value)

        if hasattr(self, 'app_context'):
            self.template_value['can_register'] = self.app_context.get_environ(
            )['reg_form']['can_register']

        if user:
            email = user.email()
            self.template_value['email_no_domain_name'] = (
                email[:email.find('@')] if '@' in email else email)
            self.template_value['email'] = email
            self.template_value['logoutUrl'] = (users.create_logout_url(
                self.request.uri))
            self.template_value['transient_student'] = False

            # configure page events
            self.template_value['record_tag_events'] = (
                CAN_PERSIST_TAG_EVENTS.value)
            self.template_value['record_page_events'] = (
                CAN_PERSIST_PAGE_EVENTS.value)
            self.template_value['record_events'] = (
                CAN_PERSIST_ACTIVITY_EVENTS.value)
            self.template_value['event_xsrf_token'] = (
                XsrfTokenManager.create_xsrf_token('event-post'))
            ## ROSEbotics ##
            namespace = namespace_manager.get_namespace()
            namespace_manager.set_namespace('')
            rosebotics_student = RoseboticsStudent.get_by_id(email.lower())
            if rosebotics_student is None:
                rosebotics_student = RoseboticsStudent(id=user.email().lower())
                rosebotics_student.put()
            recent_track_utils.set_recent_track(rosebotics_student.key,
                                                self.request.path_qs)
            most_recent_course = recent_track_utils.get_most_recent_course(
                rosebotics_student.key)
            if most_recent_course is not None:
                self.template_value["most_recent_track"] = most_recent_course
            self.template_value.update(
                recent_track_utils.get_recent_tracks(rosebotics_student.key))
            self.template_value["logout_url"] = users.create_logout_url("/")
            self.template_value["rosebotics_student"] = rosebotics_student
            namespace_manager.set_namespace(namespace)
            ## END ##
        else:
            self.template_value['loginUrl'] = users.create_login_url(
                self.request.uri)
            self.template_value["login_url"] = users.create_login_url(
                self.request.uri)
            self.template_value['transient_student'] = True
            return None

        return user
Пример #3
0
    def personalize_page_and_get_user(self):
        """If the user exists, add personalized fields to the navbar."""
        user = self.get_user()
        PageInitializerService.get().initialize(self.template_value)

        if hasattr(self, 'app_context'):
            self.template_value['can_register'] = self.app_context.get_environ(
                )['reg_form']['can_register']

        if user:
            email = user.email()
            self.template_value['email_no_domain_name'] = (
                email[:email.find('@')] if '@' in email else email)
            self.template_value['email'] = email
            self.template_value['logoutUrl'] = (
                users.create_logout_url(self.request.uri))
            self.template_value['transient_student'] = False

            # configure page events
            self.template_value['record_tag_events'] = (
                CAN_PERSIST_TAG_EVENTS.value)
            self.template_value['record_page_events'] = (
                CAN_PERSIST_PAGE_EVENTS.value)
            self.template_value['record_events'] = (
                CAN_PERSIST_ACTIVITY_EVENTS.value)
            self.template_value['event_xsrf_token'] = (
                XsrfTokenManager.create_xsrf_token('event-post'))
            ## ROSEbotics ##
            namespace = namespace_manager.get_namespace()
            namespace_manager.set_namespace('')
            rosebotics_student = RoseboticsStudent.get_by_id(email.lower())
            if rosebotics_student is None:
              rosebotics_student = RoseboticsStudent(id=user.email().lower())
              rosebotics_student.put()
            recent_track_utils.set_recent_track(rosebotics_student.key, self.request.path_qs)
            most_recent_course = recent_track_utils.get_most_recent_course(rosebotics_student.key)
            if most_recent_course is not None:
              self.template_value["most_recent_track"] = most_recent_course
            self.template_value.update(recent_track_utils.get_recent_tracks(rosebotics_student.key))
            self.template_value["logout_url"] = users.create_logout_url("/")
            self.template_value["rosebotics_student"] = rosebotics_student
            namespace_manager.set_namespace(namespace)
            ## END ##
        else:
            self.template_value['loginUrl'] = users.create_login_url(self.request.uri)
            self.template_value["login_url"] = users.create_login_url(self.request.uri)
            self.template_value['transient_student'] = True
            return None

        return user
Пример #4
0
def send_invite_email(email):
    student = RoseboticsStudent.get_by_id(email)
    if student is None:
        return
    if mail.is_email_valid(student.alt_email):
        email = [email, student.alt_email]
    message = mail.EmailMessage(
        sender="*****@*****.**")
    message.to = email
    message.subject = "ROSEbotics Team Invite"
    message.body = """ 
Hello,

You've been invited to join a ROSEbotics Team! Teams is a place where you can create study groups and monitor others progress within the courses on the website. 
    
You can see your pending invites at: http://www.rosebotics.org/teams/#/invites/

Happy Learning!

-- The ROSEbotics Team
     """.strip()
    try:
        message.send()
        logging.info("Invite Email should have been sent to: " + str(email))
    except Exception, e:
        logging.warn("Invite Email not sent to: " + str(email) + str(e))
Пример #5
0
def send_invite_email(email):
    student = RoseboticsStudent.get_by_id(email)
    if student is None:
        return
    if mail.is_email_valid(student.alt_email):
        email = [email, student.alt_email]
    message = mail.EmailMessage(sender="*****@*****.**")
    message.to = email
    message.subject = "ROSEbotics Team Invite"
    message.body = """ 
Hello,

You've been invited to join a ROSEbotics Team! Teams is a place where you can create study groups and monitor others progress within the courses on the website. 
    
You can see your pending invites at: http://www.rosebotics.org/teams/#/invites/

Happy Learning!

-- The ROSEbotics Team
     """.strip()
    try:
        message.send()
        logging.info("Invite Email should have been sent to: " + str(email))
    except Exception, e:
        logging.warn("Invite Email not sent to: " + str(email) + str(e))
Пример #6
0
 def get(self):
     user = users.get_current_user()
     if user is None:
         self.redirect("/courses")
         return
     rosebotics_student = RoseboticsStudent.get_by_id(user.email().lower())
     if rosebotics_student is None:
         self.redirect("/courses")
         return
     self.handle_redirect(rosebotics_student)
Пример #7
0
 def post(self):
     user = users.get_current_user()
     if user is None:
         self.redirect(self.request.referer)
         return
     rosebotics_student = RoseboticsStudent.get_by_id(user.email().lower())
     if rosebotics_student is None:
         self.redirect(self.request.referer)
         return
     self.handle_post(rosebotics_student)
Пример #8
0
 def post(self):
   user = users.get_current_user()
   if user is None:
     self.redirect(self.request.referer)
     return
   rosebotics_student = RoseboticsStudent.get_by_id(user.email().lower())
   if rosebotics_student is None:
     self.redirect(self.request.referer)
     return
   self.handle_post(rosebotics_student)
Пример #9
0
 def get(self):
   user = users.get_current_user()
   if user is None:
     self.redirect("/courses")
     return
   rosebotics_student = RoseboticsStudent.get_by_id(user.email().lower())
   if rosebotics_student is None:
     self.redirect("/courses")
     return
   self.handle_redirect(rosebotics_student)
Пример #10
0
 def get(self):
   values = {"page_title": self.page_title()}
   values['courses'] = COURSE_LIST
   user = users.get_current_user()
   if user:
     rosebotics_student = RoseboticsStudent.get_by_id(user.email().lower())
     if rosebotics_student is None:
       rosebotics_student = RoseboticsStudent(id=user.email().lower())
       rosebotics_student.put()
     values["logout_url"] = users.create_logout_url("/")
     values["rosebotics_student"] = rosebotics_student
     most_recent_course = recent_track_utils.get_most_recent_course(rosebotics_student.key)
     if most_recent_course is not None:
       values["most_recent_track"] = most_recent_course
     values.update(recent_track_utils.get_recent_tracks(rosebotics_student.key))
   elif self.requires_oauth():
     self.redirect("/courses")
     return
   else:
     values["login_url"] = users.create_login_url("/courses")
   self.update_values(user, values)
   template = jinja_env.get_template(self.template_file())
   self.response.out.write(template.render(values))
Пример #11
0
 def handle_job(self):
     utc = datetime.utcnow()
     for tz, offset in _tz_offsets.items():
         time = datetime(utc.year, utc.month, utc.day,
                         utc.hour) + timedelta(hours=offset)
         logging.info("Checking for sweep at: " + str(time) + " with tz: " +
                      tz)
         sweeps = AutoSweep.query(AutoSweep.time == time,
                                  AutoSweep.tz == tz)
         for sweep in sweeps:
             logging.info(sweep)
             leader_email = sweep.key.parent().string_id()
             team_leader = RoseboticsStudent.get_by_id(leader_email)
             try:
                 export_student_name = len(
                     str(sweep.options.get("student_name", ""))) > 0
                 export_rose_username = len(
                     str(sweep.options.get("rose_username", ""))) > 0
                 team_urlsafe = sweep.team_key.urlsafe()
                 timezone = sweep.options.get("timezone") or sweep.tz
                 course_progress = len(
                     str(sweep.options.get("course_progress", ""))) > 0
                 track_progress = len(
                     str(sweep.options.get("track_progress", ""))) > 0
                 unit_points = len(str(sweep.options.get("ppu", ""))) > 0
                 ppu = float(sweep.options.get("ppu", "1"))
                 ppt = float(sweep.options.get("ppt", "1"))
                 csv_data = get_csv_export_lists(team_leader, team_urlsafe,
                                                 export_student_name,
                                                 export_rose_username,
                                                 unit_points, ppu, ppt,
                                                 course_progress,
                                                 track_progress, timezone)
                 self.response.headers['Content-Type'] = 'application/csv'
                 mem_stream = StringIO.StringIO()
                 writer = csv.writer(mem_stream)
                 for csv_row in csv_data:
                     writer.writerow(csv_row)
                 self.send_email_with_attachment(
                     leader_email, "You've received an AutoSweep!",
                     mem_stream.getvalue())
                 mem_stream.close()
             except Exception, e:
                 import traceback
                 traceback.print_exc()
                 logging.error(e)
                 self.send_email(
                     leader_email,
                     "ERROR: Sorry there was an error generating your AutoSweep"
                 )
Пример #12
0
 def get_team_invites(self, empty):
     """ Get all of the invites to teams that you have """
     user_email = get_user_email()
     response = TeamInvites()
     query = RoseboticsTeamMember.query(RoseboticsTeamMember.email == user_email)
     for team_member in query:
         team = team_member.key.parent().get()
         invite = TeamInvite()
         team_leader = RoseboticsStudent.get_by_id(team.leader)
         invite.team_leader_name = team_leader.name
         invite.team_key = team.key
         invite.team_name = team.name
         invite.response = team_member.visibility
         response.invites.append(invite)
     return response
Пример #13
0
 def get_team_invites(self, empty):
     """ Get all of the invites to teams that you have """
     user_email = get_user_email()
     response = TeamInvites()
     query = RoseboticsTeamMember.query(
         RoseboticsTeamMember.email == user_email)
     for team_member in query:
         team = team_member.key.parent().get()
         invite = TeamInvite()
         team_leader = RoseboticsStudent.get_by_id(team.leader)
         invite.team_leader_name = team_leader.name
         invite.team_key = team.key
         invite.team_name = team.name
         invite.response = team_member.visibility
         response.invites.append(invite)
     return response
Пример #14
0
 def get_total_progress(self, team_progress):
     """ Gets total ROSEbotics progress for everyone in a team """
     user_email = get_user_email()
     rosebotics_team = team_progress.team_key.get()
     team_progress.name = rosebotics_team.name
     # change to filter by visibility?
     members = RoseboticsTeamMember.query(ancestor=team_progress.team_key)
     members_progress = []
     allowed_visibilies = [TeamVisibility.ALL_MEMBERS]
     if rosebotics_team.leader == user_email:
         allowed_visibilies.append(TeamVisibility.TEAM_LEADER)
     else:
         is_user_not_in_team = True
         for member in members:
             if member.email == user_email:
                 is_user_not_in_team = False
                 break
         if is_user_not_in_team:
             raise endpoints.BadRequestException(
                 "You are not allowed to view this team!")
     courses = rosebotics_team.courses
     for member in members:
         if member.visibility in allowed_visibilies or member.email == user_email:
             mp = MemberProgress()
             student = RoseboticsStudent.get_by_id(member.email.lower())
             if student is None:
                 logging.info(member.email + " being thrown out of sweep!")
                 continue
             mp.display_name = student.name
             mp.username = student.username
             for course in courses:
                 course = get_course(course)
                 if course.coming_soon:
                     continue
                 progress = get_total_progress_for_course(
                     member.email, course.prefix)
                 mp.course_progress.append(
                     create_course_progress(course.short_title, progress,
                                            course.prefix))
             members_progress.append(mp)
     team_progress.members_progress = members_progress
     return team_progress
Пример #15
0
 def get_total_progress(self, team_progress):
     """ Gets total ROSEbotics progress for everyone in a team """
     user_email = get_user_email()
     rosebotics_team = team_progress.team_key.get()
     team_progress.name = rosebotics_team.name
     # change to filter by visibility?
     members = RoseboticsTeamMember.query(ancestor=team_progress.team_key)
     members_progress = []
     allowed_visibilies = [TeamVisibility.ALL_MEMBERS]
     if rosebotics_team.leader == user_email:
         allowed_visibilies.append(TeamVisibility.TEAM_LEADER)
     else:
         is_user_not_in_team = True
         for member in members:
             if member.email == user_email:
                 is_user_not_in_team = False
                 break
         if is_user_not_in_team:
             raise endpoints.BadRequestException("You are not allowed to view this team!")
     courses = rosebotics_team.courses
     for member in members:
         if member.visibility in allowed_visibilies or member.email == user_email:
             mp = MemberProgress()
             student = RoseboticsStudent.get_by_id(member.email.lower())
             if student is None:
                 logging.info(member.email + " being thrown out of sweep!")
                 continue
             mp.display_name = student.name
             mp.username = student.username
             for course in courses:
                 course = get_course(course)
                 if course.coming_soon:
                     continue
                 progress = get_total_progress_for_course(member.email, course.prefix)
                 mp.course_progress.append(create_course_progress(course.short_title, progress, course.prefix))
             members_progress.append(mp)
     team_progress.members_progress = members_progress
     return team_progress
Пример #16
0
def get_csv_export_lists(rosebotics_student, team_urlsafe, export_student_name,
                         export_rose_username, unit_points, ppu, ppt,
                         export_course_progress, export_track_progress,
                         timezone):
    table_data = []
    header_row = []
    table_data.append(header_row)
    # Student Header
    if export_student_name:
        header_row.append("Full Name")
    if export_rose_username:
        header_row.append("Username")
    if timezone:
        header_row.append("Timestamp")
    team = ndb.Key(urlsafe=team_urlsafe).get()
    if team is None:
        return []
    members = RoseboticsTeamMember.query(ancestor=team.key)
    allowed_visibilies = [TeamVisibility.ALL_MEMBERS]
    if team.leader == rosebotics_student.key.string_id():
        allowed_visibilies.append(TeamVisibility.TEAM_LEADER)
    else:
        is_user_not_in_team = True
        for member in members:
            if member.email == rosebotics_student.key.string_id():
                is_user_not_in_team = False
                break
        if is_user_not_in_team:
            return []
    is_first_student = True
    for member in members:
        if member.visibility not in allowed_visibilies:
            continue
        student = RoseboticsStudent.get_by_id(member.email)
        if student is None:
            continue
        table_row = []
        if export_student_name:
            table_row.append(student.name)
        if export_rose_username:
            table_row.append(student.username)
        if timezone:
            table_row.append(_tz_now(timezone))
        for course in team.courses:
            course_progress = get_total_progress_for_course(
                member.email,
                course,
                as_percent=unit_points,
                get_total_tasks=True)
            course_added = False
            for track in course_progress['tracks']:
                track_progress = track['track']
                track_data = track['units']
                track_added = False
                extract_key = lambda pair: int(pair[0].split(":")[0])
                unit_tuples = sorted(track_data.items(), key=extract_key)
                for unit_id, unit_progress in unit_tuples:
                    if unit_id.endswith('-total'):
                        continue
                    unit_name = unit_id.split(':')[1]
                    if export_course_progress and not course_added:
                        table_row.append(course_progress['course'])
                        if is_first_student:
                            header_row.append(course)
                        course_added = True
                    if export_track_progress and not track_added:
                        table_row.append(track_progress)
                        if is_first_student:
                            header_row.append(track['name'])
                        track_added = True
                    if unit_points:
                        table_row.append(unit_progress * ppu)
                        unit_total = ppu
                    else:
                        table_row.append(unit_progress * ppt)
                        unit_total = track_data[unit_id + '-total'] * ppt
                    if is_first_student:
                        header_row.append(unit_name + " (out of " +
                                          str(unit_total) + ")")
        is_first_student = False
        table_data.append(table_row)
    return table_data
Пример #17
0
 def insert_team(self, team):
     """ Creates or updates a team that you own """
     user_email = get_user_email()
     if team.team_key:
         old_team = team.team_key.get()
     else:
         old_team = None
     if old_team is not None:
         old_team.name = team.name
         old_team.courses = team.courses
         old_team.put()
         old_members = RoseboticsTeamMember.query(ancestor=team.team_key)
         new_emails = []
         old_emails = [member.email for member in old_members]
         # if new email is NOT in old_members: add new email
         for member in team.members:
             if "@rose-hulman.edu" in member.email:
                 username = member.email.split("@")[0]
                 student = RoseboticsStudent.query(RoseboticsStudent.username == username).get()
                 if student is not None:
                     member.email = student.key.string_id()
                 else:
                     send_rose_invite_email(member.email)
             new_emails.append(member.email)
             if member.email not in old_emails:
                 member_key = get_member_key(team.team_key, member.email)
                 new_member = RoseboticsTeamMember(key=member_key)
                 new_member.email = member.email
                 if new_member.email == user_email:
                     new_member.visibility = TeamVisibility.ALL_MEMBERS
                 elif is_admin_user(user_email) and "@rose-hulman.edu" not in new_member.email:
                     new_member.visibility = TeamVisibility.TEAM_LEADER
                 else:
                     send_invite_email(member.email)
                 new_member.put()
         # if old username is NOT in new_members remove old member
         for old_member in old_members:
             if old_member.email not in new_emails:
                 old_member.key.delete()
     else:
         new_team = RoseboticsTeam(leader=user_email, name=team.name, courses=team.courses)
         team.team_key = new_team.put()
         emails = [member.email for member in team.members]
         for email in emails:
             student_email = email
             if "@rose-hulman.edu" in student_email:
                 username = student_email.split("@")[0]
                 student = RoseboticsStudent.query(RoseboticsStudent.username == username).get()
                 if student is not None:
                     student_email = student.key.string_id()
                 else:
                     send_rose_invite_email(student_email)
             member_key = get_member_key(team.team_key, student_email)
             new_member = RoseboticsTeamMember(key=member_key)
             new_member.email = student_email
             if new_member.email == user_email:
                 new_member.visibility = TeamVisibility.ALL_MEMBERS
             elif is_admin_user(user_email) and "@rose-hulman.edu" not in student_email:
                 new_member.visibility = TeamVisibility.TEAM_LEADER
             else:
                 send_invite_email(email)
             new_member.put()
     return team
Пример #18
0
def get_csv_export_lists(
    rosebotics_student,
    team_urlsafe,
    export_student_name,
    export_rose_username,
    unit_points,
    ppu,
    ppt,
    export_course_progress,
    export_track_progress,
    timezone,
):
    table_data = []
    header_row = []
    table_data.append(header_row)
    # Student Header
    if export_student_name:
        header_row.append("Full Name")
    if export_rose_username:
        header_row.append("Username")
    if timezone:
        header_row.append("Timestamp")
    team = ndb.Key(urlsafe=team_urlsafe).get()
    if team is None:
        return []
    members = RoseboticsTeamMember.query(ancestor=team.key)
    allowed_visibilies = [TeamVisibility.ALL_MEMBERS]
    if team.leader == rosebotics_student.key.string_id():
        allowed_visibilies.append(TeamVisibility.TEAM_LEADER)
    else:
        is_user_not_in_team = True
        for member in members:
            if member.email == rosebotics_student.key.string_id():
                is_user_not_in_team = False
                break
        if is_user_not_in_team:
            return []
    is_first_student = True
    for member in members:
        if member.visibility not in allowed_visibilies:
            continue
        student = RoseboticsStudent.get_by_id(member.email)
        if student is None:
            continue
        table_row = []
        if export_student_name:
            table_row.append(student.name)
        if export_rose_username:
            table_row.append(student.username)
        if timezone:
            table_row.append(_tz_now(timezone))
        for course in team.courses:
            course_progress = get_total_progress_for_course(
                member.email, course, as_percent=unit_points, get_total_tasks=True
            )
            course_added = False
            for track in course_progress["tracks"]:
                track_progress = track["track"]
                track_data = track["units"]
                track_added = False
                extract_key = lambda pair: int(pair[0].split(":")[0])
                unit_tuples = sorted(track_data.items(), key=extract_key)
                for unit_id, unit_progress in unit_tuples:
                    if unit_id.endswith("-total"):
                        continue
                    unit_name = unit_id.split(":")[1]
                    if export_course_progress and not course_added:
                        table_row.append(course_progress["course"])
                        if is_first_student:
                            header_row.append(course)
                        course_added = True
                    if export_track_progress and not track_added:
                        table_row.append(track_progress)
                        if is_first_student:
                            header_row.append(track["name"])
                        track_added = True
                    if unit_points:
                        table_row.append(unit_progress * ppu)
                        unit_total = ppu
                    else:
                        table_row.append(unit_progress * ppt)
                        unit_total = track_data[unit_id + "-total"] * ppt
                    if is_first_student:
                        header_row.append(unit_name + " (out of " + str(unit_total) + ")")
        is_first_student = False
        table_data.append(table_row)
    return table_data
Пример #19
0
 def insert_team(self, team):
     """ Creates or updates a team that you own """
     user_email = get_user_email()
     if team.team_key:
         old_team = team.team_key.get()
     else:
         old_team = None
     if old_team is not None:
         old_team.name = team.name
         old_team.courses = team.courses
         old_team.put()
         old_members = RoseboticsTeamMember.query(ancestor=team.team_key)
         new_emails = []
         old_emails = [member.email for member in old_members]
         # if new email is NOT in old_members: add new email
         for member in team.members:
             if "@rose-hulman.edu" in member.email:
                 username = member.email.split("@")[0]
                 student = RoseboticsStudent.query(
                     RoseboticsStudent.username == username).get()
                 if student is not None:
                     member.email = student.key.string_id()
                 else:
                     send_rose_invite_email(member.email)
             new_emails.append(member.email)
             if member.email not in old_emails:
                 member_key = get_member_key(team.team_key, member.email)
                 new_member = RoseboticsTeamMember(key=member_key)
                 new_member.email = member.email
                 if new_member.email == user_email:
                     new_member.visibility = TeamVisibility.ALL_MEMBERS
                 elif is_admin_user(
                         user_email
                 ) and "@rose-hulman.edu" not in new_member.email:
                     new_member.visibility = TeamVisibility.TEAM_LEADER
                 else:
                     send_invite_email(member.email)
                 new_member.put()
         # if old username is NOT in new_members remove old member
         for old_member in old_members:
             if old_member.email not in new_emails:
                 old_member.key.delete()
     else:
         new_team = RoseboticsTeam(leader=user_email,
                                   name=team.name,
                                   courses=team.courses)
         team.team_key = new_team.put()
         emails = [member.email for member in team.members]
         for email in emails:
             student_email = email
             if "@rose-hulman.edu" in student_email:
                 username = student_email.split("@")[0]
                 student = RoseboticsStudent.query(
                     RoseboticsStudent.username == username).get()
                 if student is not None:
                     student_email = student.key.string_id()
                 else:
                     send_rose_invite_email(student_email)
             member_key = get_member_key(team.team_key, student_email)
             new_member = RoseboticsTeamMember(key=member_key)
             new_member.email = student_email
             if new_member.email == user_email:
                 new_member.visibility = TeamVisibility.ALL_MEMBERS
             elif is_admin_user(
                     user_email
             ) and "@rose-hulman.edu" not in student_email:
                 new_member.visibility = TeamVisibility.TEAM_LEADER
             else:
                 send_invite_email(email)
             new_member.put()
     return team