def fetch_courses(self, term, verbose=False): """ Get all courses for the given term. Parameters: ----------- term : Term The term to fetch courses for. verbose : bool [default False] Whether or not to show messages throughout the process of fetching courses. """ if verbose: self.stdout.write('Fetching data...') response = requests.post( url=COURSE_URL, data={ 'term': term.to_code(), } ) if verbose: self.stdout.write('Parsing data...') root = ElementTree.fromstring(response.text.encode('utf-8')) course_count = len(root) bar_count = 40 old_crns = set([c.crn for c in Course.objects.filter(term=term)]) crns = set() if verbose: self.stdout.write('Building courses...') for i, course in enumerate(root): if verbose: count = int(float(i + 1) / course_count * bar_count) log = '[' + '=' * count + ' ' * (bar_count - count) + ']' self.stdout.write(log, ending='\r') self.stdout.flush() course_json = {} for attr in course: name = ATTRIBUTE_MAP.get(attr.tag, attr.tag) course_json[name] = attr.text try: schedules = [] try: old_course = Course.objects.get(crn=course_json['crn'], term=term) schedules = [(s.schedule, s.shown) for s in old_course.courseshown_set.all()] old_course.delete() except Course.DoesNotExist: pass course = Course.from_json(course_json, term) crns.add(course.crn) for schedule, shown in schedules: schedule.set_shown(course, shown) except Exception: self.stdout.write('Error parsing course:') self.stdout.write(str(course_json)) traceback.print_exc(file=self.stdout) self.stdout.write('\n') # Remove stale courses for crn in old_crns - crns: Course.objects.get(crn=crn, term=term).delete()