Esempio n. 1
0
async def packages_unnotify(request: Request,
                            package_ids: List[int] = [],
                            **kwargs):
    if not package_ids:
        # TODO: This error does not yet have a translation.
        return (False,
                ["You did not select any packages for notification removal."])

    # TODO: This error does not yet have a translation.
    error_tuple = (False, [
        "A package you selected does not have notifications enabled."
    ])

    bases = set()
    package_ids = set(package_ids)
    packages = db.query(models.Package).filter(
        models.Package.ID.in_(package_ids)).all()

    for pkg in packages:
        if pkg.PackageBase not in bases:
            bases.update({pkg.PackageBase})

    # Perform some checks on what the user selected for notify.
    for pkgbase in bases:
        notif = db.query(
            pkgbase.notifications.filter(models.PackageNotification.UserID ==
                                         request.user.ID).exists()).scalar()
        if not notif:
            return error_tuple

    for pkgbase in bases:
        pkgbase_actions.pkgbase_unnotify_instance(request, pkgbase)

    # TODO: This message does not yet have a translation.
    return (True, ["The selected packages' notifications have been removed."])
Esempio n. 2
0
    def __init__(self, uid, reqid, reqtype, pkgbase_id, merge_into=None):

        self._user = db.query(
            User.Username).filter(User.ID == uid).first().Username
        self._pkgbase = db.query(
            PackageBase.Name).filter(PackageBase.ID == pkgbase_id).first().Name

        self._to = aurweb.config.get('options', 'aur_request_ml')

        query = db.query(PackageRequest).join(PackageBase).join(
            PackageComaintainer,
            PackageComaintainer.PackageBaseID == PackageRequest.PackageBaseID,
            isouter=True).join(
                User,
                or_(User.ID == PackageRequest.UsersID,
                    User.ID == PackageBase.MaintainerUID,
                    User.ID == PackageComaintainer.UsersID)).filter(
                        and_(PackageRequest.ID == reqid,
                             User.Suspended == 0)).with_entities(
                                 User.Email).distinct()
        self._cc = [u.Email for u in query]

        pkgreq = db.query(PackageRequest.Comments).filter(
            PackageRequest.ID == reqid).first()

        self._text = pkgreq.Comments
        self._reqid = int(reqid)
        self._reqtype = reqtype
        self._merge_into = merge_into
Esempio n. 3
0
def test_aurblup(alpm_db: AlpmDatabase):
    # Test that we can add a package.
    alpm_db.add("pkg", "1.0", "x86_64", provides=["pkg2", "pkg3"])
    alpm_db.add("pkg2", "2.0", "x86_64")
    aurblup.main()

    # Test that the package got added to the database.
    for name in ("pkg", "pkg2"):
        pkg = db.query(OfficialProvider).filter(
            OfficialProvider.Name == name).first()
        assert pkg is not None

    # Test that we can remove the package.
    alpm_db.remove("pkg")

    # Run aurblup again with forced repository update.
    aurblup.main(True)

    # Expect that the database got updated accordingly.
    pkg = db.query(OfficialProvider).filter(
        OfficialProvider.Name == "pkg").first()
    assert pkg is None
    pkg2 = db.query(OfficialProvider).filter(
        OfficialProvider.Name == "pkg2").first()
    assert pkg2 is not None
Esempio n. 4
0
    async def authenticate(self, conn: HTTPConnection):
        unauthenticated = (None, AnonymousUser())
        sid = conn.cookies.get("AURSID")
        if not sid:
            return unauthenticated

        timeout = aurweb.config.getint("options", "login_timeout")
        remembered = ("AURREMEMBER" in conn.cookies
                      and bool(conn.cookies.get("AURREMEMBER")))
        if remembered:
            timeout = aurweb.config.getint("options",
                                           "persistent_cookie_timeout")

        # If no session with sid and a LastUpdateTS now or later exists.
        now_ts = time.utcnow()
        record = db.query(Session).filter(Session.SessionID == sid).first()
        if not record:
            return unauthenticated
        elif record.LastUpdateTS < (now_ts - timeout):
            with db.begin():
                db.delete_all([record])
            return unauthenticated

        # At this point, we cannot have an invalid user if the record
        # exists, due to ForeignKey constraints in the schema upheld
        # by mysqlclient.
        with db.begin():
            user = db.query(User).filter(User.ID == record.UsersID).first()
        user.nonce = util.make_nonce()
        user.authenticated = True

        return (AuthCredentials(["authenticated"]), user)
Esempio n. 5
0
    def __init__(self, uid, reqid, reason):
        user = db.query(User.Username).filter(User.ID == uid).first()
        self._user = user.Username if user else None

        self._to = aurweb.config.get('options', 'aur_request_ml')

        query = db.query(PackageRequest).join(PackageBase).join(
            PackageComaintainer,
            PackageComaintainer.PackageBaseID == PackageRequest.PackageBaseID,
            isouter=True).join(
                User,
                or_(User.ID == PackageRequest.UsersID,
                    User.ID == PackageBase.MaintainerUID,
                    User.ID == PackageComaintainer.UsersID)).filter(
                        and_(PackageRequest.ID == reqid,
                             User.Suspended == 0)).with_entities(
                                 User.Email).distinct()
        self._cc = [u.Email for u in query]

        pkgreq = db.query(PackageRequest).join(RequestType).filter(
            PackageRequest.ID == reqid).with_entities(
                PackageRequest.ClosureComment, RequestType.Name,
                PackageRequest.PackageBaseName).first()

        self._text = pkgreq.ClosureComment
        self._reqtype = pkgreq.Name
        self._pkgbase = pkgreq.PackageBaseName

        self._reqid = int(reqid)
        self._reason = reason
Esempio n. 6
0
async def trusted_user_proposal(request: Request, proposal: int):
    if not request.user.has_credential(creds.TU_LIST_VOTES):
        return RedirectResponse("/tu", status_code=HTTPStatus.SEE_OTHER)

    context = await make_variable_context(request, "Trusted User")
    proposal = int(proposal)

    voteinfo = db.query(
        models.TUVoteInfo).filter(models.TUVoteInfo.ID == proposal).first()
    if not voteinfo:
        raise HTTPException(status_code=HTTPStatus.NOT_FOUND)

    voters = db.query(models.User).join(
        models.TUVote).filter(models.TUVote.VoteID == voteinfo.ID)
    vote = db.query(models.TUVote).filter(
        and_(models.TUVote.UserID == request.user.ID,
             models.TUVote.VoteID == voteinfo.ID)).first()
    if not request.user.has_credential(creds.TU_VOTE):
        context["error"] = "Only Trusted Users are allowed to vote."
    if voteinfo.User == request.user.Username:
        context["error"] = "You cannot vote in an proposal about you."
    elif vote is not None:
        context["error"] = "You've already voted for this proposal."

    context["vote"] = vote
    return render_proposal(request, context, proposal, voteinfo, voters, vote)
Esempio n. 7
0
def is_banned(request: Request = None, **kwargs) -> None:
    host = request.client.host
    exists = db.query(models.Ban, models.Ban.IPAddress == host).exists()
    if db.query(exists).scalar():
        raise ValidationError([
            "Account registration has been disabled for your "
            "IP address, probably due to sustained spam attacks. "
            "Sorry for the inconvenience."
        ])
Esempio n. 8
0
def test_request_type_name_display():
    deletion = db.query(RequestType, RequestType.ID == DELETION_ID).first()
    assert deletion.name_display() == "Deletion"

    orphan = db.query(RequestType, RequestType.ID == ORPHAN_ID).first()
    assert orphan.name_display() == "Orphan"

    merge = db.query(RequestType, RequestType.ID == MERGE_ID).first()
    assert merge.name_display() == "Merge"
Esempio n. 9
0
def pkgname_link(pkgname: str) -> str:
    record = db.query(Package).filter(Package.Name == pkgname).exists()
    if db.query(record).scalar():
        return f"/packages/{pkgname}"

    official = db.query(OfficialProvider).filter(
        OfficialProvider.Name == pkgname).exists()
    if db.query(official).scalar():
        base = "/".join([OFFICIAL_BASE, "packages"])
        return f"{base}/?q={pkgname}"
Esempio n. 10
0
    def __init__(self, vote_id):
        self._vote_id = int(vote_id)

        subquery = db.query(TUVote.UserID).filter(TUVote.VoteID == vote_id)
        query = db.query(User).filter(
            and_(User.AccountTypeID.in_((2, 4)), ~User.ID.in_(subquery),
                 User.Suspended == 0)).with_entities(User.Email,
                                                     User.LangPreference)
        self._recipients = [(u.Email, u.LangPreference) for u in query]

        super().__init__()
Esempio n. 11
0
def email_in_use(E: str = str(),
                 user: models.User = None,
                 _: l10n.Translator = None,
                 **kwargs) -> None:
    exists = db.query(models.User).filter(
        and_(models.User.ID != user.ID, models.User.Email == E)).exists()
    if db.query(exists).scalar():
        # If the email already exists...
        raise ValidationError([
            _("The address, %s%s%s, is already in use.") %
            ("<strong>", E, "</strong>")
        ])
Esempio n. 12
0
def username_in_use(U: str = str(),
                    user: models.User = None,
                    _: l10n.Translator = None,
                    **kwargs) -> None:
    exists = db.query(models.User).filter(
        and_(models.User.ID != user.ID, models.User.Username == U)).exists()
    if db.query(exists).scalar():
        # If the username already exists...
        raise ValidationError([
            _("The username, %s%s%s, is already in use.") %
            ("<strong>", U, "</strong>")
        ])
Esempio n. 13
0
    def __init__(self, uid, pkgbase_id):

        self._pkgbase = db.query(
            PackageBase.Name).filter(PackageBase.ID == pkgbase_id).first().Name

        user = db.query(User).filter(User.ID == uid).with_entities(
            User.Email, User.LangPreference).first()

        self._to = user.Email
        self._lang = user.LangPreference

        super().__init__()
Esempio n. 14
0
def test_create_delete():
    with db.begin():
        account_type = db.create(AccountType, AccountType="test")

    record = db.query(AccountType, AccountType.AccountType == "test").first()
    assert record is not None

    with db.begin():
        db.delete(account_type)

    record = db.query(AccountType, AccountType.AccountType == "test").first()
    assert record is None
Esempio n. 15
0
async def trusted_user_proposal_post(request: Request,
                                     proposal: int,
                                     decision: str = Form(...)):
    if not request.user.has_credential(creds.TU_LIST_VOTES):
        return RedirectResponse("/tu", status_code=HTTPStatus.SEE_OTHER)

    context = await make_variable_context(request, "Trusted User")
    proposal = int(proposal)  # Make sure it's an int.

    voteinfo = db.query(
        models.TUVoteInfo).filter(models.TUVoteInfo.ID == proposal).first()
    if not voteinfo:
        raise HTTPException(status_code=HTTPStatus.NOT_FOUND)

    voters = db.query(models.User).join(
        models.TUVote).filter(models.TUVote.VoteID == voteinfo.ID)
    vote = db.query(models.TUVote).filter(
        and_(models.TUVote.UserID == request.user.ID,
             models.TUVote.VoteID == voteinfo.ID)).first()

    status_code = HTTPStatus.OK
    if not request.user.has_credential(creds.TU_VOTE):
        context["error"] = "Only Trusted Users are allowed to vote."
        status_code = HTTPStatus.UNAUTHORIZED
    elif voteinfo.User == request.user.Username:
        context["error"] = "You cannot vote in an proposal about you."
        status_code = HTTPStatus.BAD_REQUEST
    elif vote is not None:
        context["error"] = "You've already voted for this proposal."
        status_code = HTTPStatus.BAD_REQUEST

    if status_code != HTTPStatus.OK:
        return render_proposal(request,
                               context,
                               proposal,
                               voteinfo,
                               voters,
                               vote,
                               status_code=status_code)

    if decision in {"Yes", "No", "Abstain"}:
        # Increment whichever decision was given to us.
        setattr(voteinfo, decision, getattr(voteinfo, decision) + 1)
    else:
        return Response("Invalid 'decision' value.",
                        status_code=HTTPStatus.BAD_REQUEST)

    with db.begin():
        vote = db.create(models.TUVote, User=request.user, VoteInfo=voteinfo)

    context["error"] = "You've already voted for this proposal."
    return render_proposal(request, context, proposal, voteinfo, voters, vote)
Esempio n. 16
0
def test_relation_types():
    conflicts = db.query(RelationType,
                         RelationType.Name == "conflicts").first()
    assert conflicts is not None
    assert conflicts.Name == "conflicts"

    provides = db.query(RelationType, RelationType.Name == "provides").first()
    assert provides is not None
    assert provides.Name == "provides"

    replaces = db.query(RelationType, RelationType.Name == "replaces").first()
    assert replaces is not None
    assert replaces.Name == "replaces"
Esempio n. 17
0
def get_extended_fields():
    subqueries = [
        # PackageDependency
        db.query(models.PackageDependency
                 ).join(models.DependencyType).with_entities(
                     models.PackageDependency.PackageID.label("ID"),
                     models.DependencyType.Name.label("Type"),
                     models.PackageDependency.DepName.label("Name"),
                     models.PackageDependency.DepCondition.label("Cond")
                 ).distinct().order_by("Name"),

        # PackageRelation
        db.query(models.PackageRelation
                 ).join(models.RelationType).with_entities(
                     models.PackageRelation.PackageID.label("ID"),
                     models.RelationType.Name.label("Type"),
                     models.PackageRelation.RelName.label("Name"),
                     models.PackageRelation.RelCondition.label("Cond")
                 ).distinct().order_by("Name"),

        # Groups
        db.query(models.PackageGroup).join(
            models.Group,
            models.PackageGroup.GroupID == models.Group.ID).with_entities(
                models.PackageGroup.PackageID.label("ID"),
                literal("Groups").label("Type"),
                models.Group.Name.label("Name"),
                literal(str()).label("Cond")).distinct().order_by("Name"),

        # Licenses
        db.query(models.PackageLicense).join(
            models.License, models.PackageLicense.LicenseID ==
            models.License.ID).with_entities(
                models.PackageLicense.PackageID.label("ID"),
                literal("License").label("Type"),
                models.License.Name.label("Name"),
                literal(str()).label("Cond")).distinct().order_by("Name"),

        # Keywords
        db.query(models.PackageKeyword).join(
            models.Package, Package.PackageBaseID ==
            models.PackageKeyword.PackageBaseID).with_entities(
                models.Package.ID.label("ID"),
                literal("Keywords").label("Type"),
                models.PackageKeyword.Keyword.label("Name"),
                literal(str()).label("Cond")).distinct().order_by("Name")
    ]
    query = subqueries[0].union_all(*subqueries[1:])
    return get_extended_dict(query)
Esempio n. 18
0
async def check_terms_of_service(request: Request, call_next: typing.Callable):
    """ This middleware function redirects authenticated users if they
    have any outstanding Terms to agree to. """
    if request.user.is_authenticated() and request.url.path != "/tos":
        unaccepted = query(Term).join(AcceptedTerm).filter(
            or_(
                AcceptedTerm.UsersID != request.user.ID,
                and_(AcceptedTerm.UsersID == request.user.ID,
                     AcceptedTerm.TermsID == Term.ID,
                     AcceptedTerm.Revision < Term.Revision)))
        if query(Term).count() > unaccepted.count():
            return RedirectResponse("/tos",
                                    status_code=int(http.HTTPStatus.SEE_OTHER))

    return await util.error_or_result(call_next, request)
Esempio n. 19
0
    def __init__(self, uid, pkgbase_id):

        self._user = db.query(
            User.Username).filter(User.ID == uid).first().Username
        self._pkgbase = db.query(
            PackageBase.Name).filter(PackageBase.ID == pkgbase_id).first().Name

        query = db.query(User).join(PackageNotification).filter(
            and_(User.UpdateNotify == 1, PackageNotification.UserID != uid,
                 PackageNotification.PackageBaseID == pkgbase_id,
                 User.Suspended == 0)).with_entities(
                     User.Email, User.LangPreference).distinct()
        self._recipients = [(u.Email, u.LangPreference) for u in query]

        super().__init__()
Esempio n. 20
0
async def requests(request: Request,
                   O: int = Query(default=defaults.O),
                   PP: int = Query(default=defaults.PP)):
    context = make_context(request, "Requests")

    context["q"] = dict(request.query_params)

    O, PP = util.sanitize_params(O, PP)
    context["O"] = O
    context["PP"] = PP

    # A PackageRequest query, with left inner joined User and RequestType.
    query = db.query(PackageRequest).join(User,
                                          User.ID == PackageRequest.UsersID)

    # If the request user is not elevated (TU or Dev), then
    # filter PackageRequests which are owned by the request user.
    if not request.user.is_elevated():
        query = query.filter(PackageRequest.UsersID == request.user.ID)

    context["total"] = query.count()
    context["results"] = query.order_by(
        # Order primarily by the Status column being PENDING_ID,
        # and secondarily by RequestTS; both in descending order.
        case([(PackageRequest.Status == PENDING_ID, 1)], else_=0).desc(),
        PackageRequest.RequestTS.desc()).limit(PP).offset(O).all()

    return render_template(request, "requests.html", context)
Esempio n. 21
0
def get_captcha_salts():
    """ Produce salts based on the current user count. """
    count = query(User).count()
    salts = []
    for i in range(0, 6):
        salts.append(f"aurweb-{count - i}")
    return salts
Esempio n. 22
0
def add_comaintainers(request: Request, pkgbase: PackageBase,
                      usernames: List[str]) -> None:
    """
    Add comaintainers to `pkgbase`.

    :param request: FastAPI request
    :param pkgbase: PackageBase instance
    :param usernames: Iterable of username strings
    :return: Error string on failure else None
    """
    # For each username in usernames, perform validation of the username
    # and append the User record to `users` if no errors occur.
    users = []
    for username in usernames:
        user = db.query(User).filter(User.Username == username).first()
        if not user:
            _ = l10n.get_translator_for_request(request)
            return _("Invalid user name: %s") % username
        users.append(user)

    notifications = []

    def add_comaint(user: User):
        nonlocal notifications
        # Populate `notifications` with add_comaintainer's return value,
        # which is a ComaintainerAddNotification.
        notifications.append(add_comaintainer(pkgbase, user))

    # Move along: add all `users` as new `pkgbase` comaintainers.
    util.apply_all(users, add_comaint)

    # Send out notifications.
    util.apply_all(notifications, lambda n: n.send())
Esempio n. 23
0
def main():
    args = parse_args()

    db.get_engine()
    type = db.query(AccountType,
                    AccountType.AccountType == args.type).first()
    with db.begin():
        user = db.create(User, Username=args.username,
                         Email=args.email, Passwd=args.password,
                         RealName=args.realname, IRCNick=args.ircnick,
                         PGPKey=args.pgp_key, AccountType=type)

    if args.ssh_pubkey:
        pubkey = args.ssh_pubkey.strip()

        # Remove host from the pubkey if it's there.
        pubkey = ' '.join(pubkey.split(' ')[:2])

        with db.begin():
            db.create(SSHPubKey,
                      User=user,
                      PubKey=pubkey,
                      Fingerprint=get_fingerprint(pubkey))

    print(user.json())
    return 0
Esempio n. 24
0
def test_request_post_deletion_as_maintainer(client: TestClient, auser: User,
                                             pkgbase: PackageBase):
    """ Test the POST route for creating a deletion request as maint works. """
    endpoint = f"/pkgbase/{pkgbase.Name}/request"
    data = {"comments": "Test request.", "type": "deletion"}
    with client as request:
        resp = request.post(endpoint, data=data, cookies=auser.cookies)
    assert resp.status_code == int(HTTPStatus.SEE_OTHER)

    # Check the pkgreq record got created and accepted.
    pkgreq = db.query(PackageRequest).first()
    assert pkgreq is not None
    assert pkgreq.ReqTypeID == DELETION_ID
    assert pkgreq.Status == ACCEPTED_ID

    # Should've gotten two emails.
    assert Email.count() == 2

    # A RequestOpenNotification should've been sent out.
    email = Email(1)
    expr = r"^\[PRQ#%d\] Deletion Request for [^ ]+$" % pkgreq.ID
    assert re.match(expr, email.headers.get("Subject"))

    # Check the content of the close notification.
    email = Email(2)
    expr = r"^\[PRQ#%d\] Deletion Request for [^ ]+ Accepted$" % pkgreq.ID
    assert re.match(expr, email.headers.get("Subject"))
Esempio n. 25
0
async def packages_unflag(request: Request,
                          package_ids: List[int] = [],
                          **kwargs):
    if not package_ids:
        return (False, ["You did not select any packages to unflag."])

    # Holds the set of package bases we're looking to unflag.
    # Constructed below via looping through the packages query.
    bases = set()

    package_ids = set(package_ids)  # Convert this to a set for O(1).
    packages = db.query(models.Package).filter(
        models.Package.ID.in_(package_ids)).all()
    for pkg in packages:
        has_cred = request.user.has_credential(
            creds.PKGBASE_UNFLAG, approved=[pkg.PackageBase.Flagger])
        if not has_cred:
            return (False, ["You did not select any packages to unflag."])

        if pkg.PackageBase not in bases:
            bases.update({pkg.PackageBase})

    for pkgbase in bases:
        pkgbase_actions.pkgbase_unflag_instance(request, pkgbase)
    return (True, ["The selected packages have been unflagged."])
Esempio n. 26
0
async def account(request: Request, username: str):
    _ = l10n.get_translator_for_request(request)
    context = await make_variable_context(
        request, _("Account") + " " + username)
    if not request.user.is_authenticated():
        return render_template(request, "account/show.html", context,
                               status_code=HTTPStatus.UNAUTHORIZED)

    # Get related User record, if possible.
    user = get_user_by_name(username)
    context["user"] = user

    # Format PGPKey for display with a space between each 4 characters.
    k = user.PGPKey or str()
    context["pgp_key"] = " ".join([k[i:i + 4] for i in range(0, len(k), 4)])

    login_ts = None
    session = db.query(models.Session).filter(
        models.Session.UsersID == user.ID).first()
    if session:
        login_ts = user.session.LastUpdateTS
    context["login_ts"] = login_ts

    # Render the template.
    return render_template(request, "account/show.html", context)
def test_tu_proposal_vote(client, proposal):
    tu_user, user, voteinfo = proposal

    # Store the current related values.
    yes = voteinfo.Yes

    cookies = {"AURSID": tu_user.login(Request(), "testPassword")}
    with client as request:
        data = {"decision": "Yes"}
        response = request.post(f"/tu/{voteinfo.ID}",
                                cookies=cookies,
                                data=data)
    assert response.status_code == int(HTTPStatus.OK)

    # Check that the proposal record got updated.
    assert voteinfo.Yes == yes + 1

    # Check that the new TUVote exists.
    vote = db.query(TUVote, TUVote.VoteInfo == voteinfo,
                    TUVote.User == tu_user).first()
    assert vote is not None

    root = parse_root(response.text)

    # Check that we're told we've voted.
    status = root.xpath('//span[contains(@class, "status")]/text()')[0]
    assert status == "You've already voted for this proposal."
Esempio n. 28
0
 def _search_by_comaintainer(self, keywords: str) -> orm.Query:
     self._join_user()
     self._join_comaint()
     user = db.query(User).filter(User.Username == keywords).first()
     uid = 0 if not user else user.ID
     self.query = self.query.filter(PackageComaintainer.UsersID == uid)
     return self
Esempio n. 29
0
def ssh_pubkey(PK: str = str(), user: models.User = None, **kwargs) -> None:
    if not PK:
        # If no pubkey is provided, wipe out any pubkeys the user
        # has and return out early.
        with db.begin():
            db.delete_all(user.ssh_pub_keys)
        return

    # Otherwise, parse ssh keys and their fprints out of PK.
    keys = util.parse_ssh_keys(PK.strip())
    fprints = [get_fingerprint(" ".join(k)) for k in keys]

    with db.begin():
        # Delete any existing keys we can't find.
        to_remove = user.ssh_pub_keys.filter(
            ~SSHPubKey.Fingerprint.in_(fprints))
        db.delete_all(to_remove)

        # For each key, if it does not yet exist, create it.
        for i, full_key in enumerate(keys):
            prefix, key = full_key
            exists = user.ssh_pub_keys.filter(
                SSHPubKey.Fingerprint == fprints[i]).exists()
            if not db.query(exists).scalar():
                # No public key exists, create one.
                db.create(models.SSHPubKey,
                          UserID=user.ID,
                          PubKey=" ".join([prefix, key]),
                          Fingerprint=fprints[i])
Esempio n. 30
0
def test_user_login_logout(user: User):
    """ Test creating a user and reading its columns. """
    # Assert that make_user created a valid user.
    assert bool(user.ID)

    # Test authentication.
    assert user.valid_password("testPassword")
    assert not user.valid_password("badPassword")

    # Make a raw request.
    request = Request()
    assert not user.login(request, "badPassword")
    assert not user.is_authenticated()

    sid = user.login(request, "testPassword")
    assert sid is not None
    assert user.is_authenticated()

    # Expect that User session relationships work right.
    user_session = db.query(Session, Session.UsersID == user.ID).first()
    assert user_session == user.session
    assert user.session.SessionID == sid
    assert user.session.User == user

    # Search for the user via query API.
    result = db.query(User, User.ID == user.ID).first()

    # Compare the result and our original user.
    assert result == user
    assert result.ID == user.ID
    assert result.AccountType.ID == user.AccountType.ID
    assert result.Username == user.Username
    assert result.Email == user.Email

    # Test result authenticate methods to ensure they work the same.
    assert not result.valid_password("badPassword")
    assert result.valid_password("testPassword")
    assert result.is_authenticated()

    # Test out user string functions.
    assert repr(user) == f"<User(ID='{user.ID}', " + \
        "AccountType='User', Username='******')>"

    # Test logout.
    user.logout(request)
    assert not user.is_authenticated()