Esempio n. 1
0
def create_group():
    form = CreateGroupForm(request.form)
    if request.method == 'POST' and form.validate():
        success = create_group_controller(form)
        if success:
            flash("Succesfully created group " + form.groupname.data + ".")
            return redirect((url_for('my_groups')))
        else:
            flash("Group creation failed; group name must be unique.")
            return render_template('groups/creategroup.html', form=form)
    else:
        return render_template('groups/creategroup.html', form=form)
Esempio n. 2
0
def group():
    # Forms
    create_group_form = CreateGroupForm()
    leave_group_form = LeaveGroupForm()
    invite_user_to_group_form = InviteUserToGroupForm()
    create_pairs_form = CreatePairsForm()
    kick_user_form = KickUserForm()

    # Args
    message = request.args.get("message")

    if request.method == "POST":
        if (create_group_form.submit_create_group_form.data
                and create_group_form.validate()):
            group_name = create_group_form.name.data
            group = Group.query.filter_by(name=group_name).first()
            if group:
                return redirect(
                    url_for(
                        ".group",
                        message=
                        f"Group with the name {group_name} already exists",
                    ))
            new_group = Group(name=group_name)
            new_group.save_to_db(db)
            new_group_assoc = GroupsAndUsersAssociation(group=new_group,
                                                        user=current_user,
                                                        group_admin=True)
            new_group_assoc.save_to_db(db)

            # TODO: @prithajnath
            # We shouldn't have to do this here. This should be taken care of by the right SQLALchemy hook
            all_admin_materialized_view.refresh()

            return redirect(url_for(".group", group_id=new_group.id))

        if (leave_group_form.submit_leave_group_form.data
                and leave_group_form.validate()):
            group_name = leave_group_form.group_name.data
            print(leave_group_form)
            print(group_name)
            group = Group.query.filter_by(name=group_name).first()

            group_assoc_with_user = GroupsAndUsersAssociation.query.filter_by(
                group=group, user=current_user).first()
            group_assoc_with_user.delete_from_db(db)
            return redirect(url_for(".group"))

        if (create_pairs_form.submit_create_pairs_form.data
                and create_pairs_form.validate()):
            print(create_pairs_form.submit_create_pairs_form.data)
            group_id = request.args.get("group_id")
            print(f"Creating pairs for {group_id}")
            group = Group.query.filter_by(id=group_id).first()

            currently_running_creation_attempt = PairCreationStatus.query.filter_by(
                group_id=group.id, status="creating").first()

            if currently_running_creation_attempt:
                message = "Pair creation already in progress"
                return redirect(
                    url_for(".group", message=message, group_id=group_id))

            pair_latest_timestamp = Pair.query.with_entities(
                func.max(Pair.timestamp)).filter_by(
                    group_id=group_id).first()[0] or datetime(1970, 1, 1)

            today = datetime.now()

            delta = today - pair_latest_timestamp
            if delta.days > 1:
                if group.is_admin(
                        current_user) and current_user.is_authenticated:

                    with AdvisoryLock(
                            engine=db.engine,
                            lock_key=group.name).grab_lock() as locked_session:
                        lock, session = locked_session
                        if lock:
                            # NOTE: Can't pass SQLAlchemy objects like group* and current_user** here because
                            # they are attached to a different session
                            creation_attempt = Task(
                                started_at=datetime.now(),
                                name="create_pairs",
                                payload={
                                    "group_id": group.id,
                                    "initiator_id": current_user.id,
                                },
                                status="starting",
                            )

                            session.add(creation_attempt)
                        else:
                            message = (
                                "Too many attempts to create pairs at the same time!"
                            )
                            return redirect(
                                url_for(".group",
                                        message=message,
                                        group_id=group_id))

                    # Again, only queue messages after lock has been released
                    task = celery.send_task("pair.create_pairs", (group_id, ))

                    if task.status == "PENDING":
                        timestamp = maya.MayaDT.from_datetime(datetime.now())
                        message = f"Pair creation has been initiated at {timestamp.__str__()}. Sit tight!"
                        return redirect(
                            url_for(".group",
                                    message=message,
                                    group_id=group_id))
            else:
                message = "This group is in cooldown (Pairs were created recently). Please try again in a day"
                return redirect(
                    url_for(".group", message=message, group_id=group_id))

        if (invite_user_to_group_form.submit_invite_form.data
                and invite_user_to_group_form.validate()):
            group_id = request.args.get("group_id")
            group = Group.query.filter_by(id=group_id).first()
            user = User.query.filter_by(
                email=invite_user_to_group_form.email.data).first()
            new_invite = EmailInvite(
                timestamp=datetime.now(),
                invited_email=invite_user_to_group_form.email.data,
                code=EmailInvite.generate_code("group"),
                payload={
                    "group_id": group.id,
                    "user_id": user.id
                } if user else {"group_id": group.id},
            )

            new_invite.save_to_db(db)

            to_email = new_invite.invited_email
            admin_first_name = current_user.first_name
            group_name = group.name

            if not user:

                _task = Task(
                    name="invite_user_to_sign_up",
                    started_at=datetime.now(),
                    status="starting",
                    payload={
                        "to_email": to_email,
                        "admin_first_name": admin_first_name,
                        "invite_code": new_invite.code,
                        "group_name": group_name,
                    },
                )

                _task.save_to_db(db)

                task = celery.send_task(
                    "user.invite_user_to_sign_up",
                    (to_email, admin_first_name, group_name),
                )

                if task.status == "PENDING":
                    return redirect(
                        url_for(
                            ".group",
                            message=
                            f"{invite_user_to_group_form.email.data} has been invited to create an account and join this group!",
                            group_id=group_id,
                            create_pairs_form=create_pairs_form,
                            form=invite_user_to_group_form,
                        ))

            else:
                _task = Task(
                    name="invite_user_to_group",
                    started_at=datetime.now(),
                    status="starting",
                    payload={
                        "to_email": to_email,
                        "admin_first_name": admin_first_name,
                        "invite_code": new_invite.code,
                        "group_name": group_name,
                    },
                )

                _task.save_to_db(db)

                task = celery.send_task(
                    "user.invite_user_to_group",
                    (to_email, admin_first_name, group_name),
                )

                if task.status == "PENDING":
                    return redirect(
                        url_for(
                            ".group",
                            message=
                            f"{invite_user_to_group_form.email.data} has been invited to join this group!",
                            group_id=group_id,
                            create_pairs_form=create_pairs_form,
                            form=invite_user_to_group_form,
                        ))

    group_id = request.args.get("group_id")
    message = request.args.get("message")
    alert = request.args.get("alert")
    group = Group.query.filter_by(id=group_id).first()

    if group:
        if GroupsAndUsersAssociation.query.filter_by(
                group_id=group.id, user_id=current_user.id).first():
            return render_template(
                "group.html",
                create_pairs_form=create_pairs_form,
                invite_user_to_group_form=invite_user_to_group_form,
                kick_user_form=kick_user_form,
                group=group,
                message=message,
                alert=alert,
            )

    GroupPreview = namedtuple("GroupPreview", "id name avatars members")
    groups = []
    for i in current_user.groups:
        group = i.group
        avatars = [j.user.avatar_url for j in group.users]
        groups.append(
            GroupPreview(group.id, group.name, avatars[:3], len(avatars)))

    return render_template(
        "my_groups.html",
        groups=groups,
        create_group_form=create_group_form,
        leave_group_form=leave_group_form,
        message=message,
        alert=alert,
    )