class Proposal(BaseProposal): """ A proposal object """ meta = {'collection': 'proposal'} # Tags tags = db.ListField(db.StringField(max_length=30)) # School the proposal was made to schools = db.ListField( db.ReferenceField(School, reverse_delete_rule=NULLIFY)) # Context in which the proposal was made source = db.IntField(default=SOURCE_WEBSITE) # Which stage in the organizing process stage = db.ListField(db.EmbeddedDocumentField(Stage)) def __init__(self, *args, **kwargs): super(Proposal, self).__init__(*args, **kwargs) if not self.id: self.interested.append(Interested(user=self.proposer)) self.num_interested = 1 self.stage.append(Stage(creator=self.proposer, date=self.created)) @property def current_stage(self): current_stage = None for s in self.stage: if current_stage is None or s.date > current_stage.date: current_stage = s return current_stage
class InterestedMixin(object): """ Mixin to provide fields for interest/ following functionality """ interested = db.ListField(db.EmbeddedDocumentField(Interested)) num_interested = db.IntField(default=0) def add_interested_user(self, user): self.update(add_to_set__interested=Interested(user=user)) self.reload() self.update(set__num_interested=len(self.interested)) self.reload() def remove_interested_user(self, user): self.update(pull__interested__user=user) self.reload() self.update(set__num_interested=len(self.interested)) self.reload() def user_is_interested(self, user): if user is None: return False for iu in self.interested: if iu.user == user: return iu return False @property def interested_users(self): return [interested.user for interested in self.interested]
class User(db.Document, UserMixin): """ A user object that integrates with Flask-Login (via UserMixin and the authenticate method) """ email = db.EmailField(unique=True) username = db.StringField(unique=True, max_length=64) display_name = db.StringField(max_length=64) password = db.StringField(max_length=256) active = db.BooleanField(default=True) role = db.IntField(default=ROLE_USER) created = db.DateTimeField(default=datetime.datetime.now()) # School/s the user is following schools = db.ListField( db.ReferenceField(School, reverse_delete_rule=NULLIFY)) available_weekday_morning = db.BooleanField(default=False) available_weekday_night = db.BooleanField(default=False) available_weekend_morning = db.BooleanField(default=False) available_weekend_night = db.BooleanField(default=False) # following which schools? (list of schools) # committee memberships (list) def __init__(self, is_admin=False, *args, **kwargs): super(User, self).__init__(*args, **kwargs) password = kwargs.get('password', None) if not self.id and password is not None: self.set_password(password) if not self.id and self.display_name is None: self.display_name = self.username if not self.id and is_admin: self.role = ROLE_ADMIN def is_admin(self): return self.role == ROLE_ADMIN def set_password(self, password): self.password = generate_password_hash(password) def check_password(self, password): if self.password is None: return False return check_password_hash(self.password, password) @classmethod def authenticate(self, login, password): """ Used by my implementation of Flask-Login """ try: user = self.objects.get(Q(username=login) | Q(email=login)) if user: authenticated = user.check_password(password) else: authenticated = False return user, authenticated except: import traceback print(traceback.format_exc()) return None, False def __str__(self): return self.display_name
class Stage(db.EmbeddedDocument): """ Structure for holding the stage of a proposal """ date = db.DateTimeField(default=datetime.datetime.now()) value = db.IntField(default=LIFE_ORIGIN) creator = db.ReferenceField(User) @property def pretty_date(self): return pretty_date(self.date)
class User(db.Document): user_id = db.IntField(unique=True) first_name = db.StringField(max_length=50) last_name = db.StringField(max_length=50) email = db.StringField(max_length=30, unique=True) password = db.StringField() def set_password(self, password): self.password = generate_password_hash(password) def get_password(self, password): return check_password_hash(self.password, password)
class Discussion(db.Document): """ Thread of comments. """ title = db.StringField(max_length=1000, required=True) # The comments and pointers to certain important comments #comments = db.SortedListField(db.ReferenceField(Comment), ordering="created", reverse=True) num_comments = db.IntField(default=0) first_comment = db.ReferenceField(Comment) last_comment = db.ReferenceField(Comment) import datetime last_comment_time = db.DateTimeField(default=datetime.datetime.now()) # Setting priority might allow for control over the ordering of discussion threads priority = db.IntField(default=0) created = db.DateTimeField(default=datetime.datetime.now()) creator = db.ReferenceField(User, reverse_delete_rule = NULLIFY) published = db.BooleanField(default=True) schools = db.ListField(db.ReferenceField(School, reverse_delete_rule = NULLIFY)) #def add_comment(self, text, user, time=None): # """ Creates a new comment and adds it to discussion thread """ # c = Comment( # creator = user, # text = text, # discussion = self, # ) # c.created = datetime.datetime.now() # c.save() #self.update(add_to_set__comments=c) #self.reload() #self.update(set__num_comments=len(self.comments)) #if not self.first_comment: # self.first_comment = c #self.last_comment = c #self.last_comment_time = c.created #self.save()
class Enrollment(db.Document): user_id = db.IntField() courseID = db.StringField(max_length=10)
class Proposal(db.Document, InterestedMixin): """ A proposal object """ meta = {'collection': 'proposal'} ## Tags #tags = db.ListField(db.StringField(max_length=30)) # School the proposal was made to schools = db.ListField(db.ReferenceField(School, reverse_delete_rule = NULLIFY)) # Context in which the proposal was made source = db.IntField(default=SOURCE_WEBSITE) # Which stage in the organizing process stage = db.ListField(db.EmbeddedDocumentField(Stage)) title = db.StringField(max_length=1000, required=True) # A copy of the original description is kept description = db.StringField(max_length=1000000, required=True) #edited_description = db.StringField() # Person who made the proposal proposer = db.ReferenceField(User, reverse_delete_rule = NULLIFY) created = db.DateTimeField(default=datetime.datetime.now()) updated = db.DateTimeField(default=datetime.datetime.now()) published = db.BooleanField(default=True) # The proposal that this proposal "copies" #copy_of = db.ReferenceField("self", reverse_delete_rule = NULLIFY) # Events events = db.ListField(db.ReferenceField(Event, reverse_delete_rule = NULLIFY)) # Discussions discussions = db.ListField(db.ReferenceField(Discussion, reverse_delete_rule = NULLIFY)) teachers = db.ListField(db.ReferenceField(User, reverse_delete_rule = NULLIFY)) def __init__(self, *args, **kwargs): super(Proposal, self).__init__(*args, **kwargs) if not self.id: self.interested.append(Interested(user=self.proposer)) self.num_interested = 1 self.stage.append(Stage(creator=self.proposer, date=self.created)) @property def current_stage(self): current_stage = None for s in self.stage: if current_stage is None or s.date>current_stage.date: current_stage = s return current_stage def add_event(self, event): self.update(add_to_set__events=event) self.reload() def remove_event(self, event): self.update(pull__events=event) self.reload() def add_discussion(self, discussion): self.update(add_to_set__discussions=discussion) self.reload() def remove_discussion(self, discussion): self.update(pull__discussions=discussion) self.reload() def __str__(self): return self.title