Ejemplo n.º 1
0
 def create_user_and_session(self):
     user = BaseUser(**self.credentials,
                     active=True,
                     admin=True,
                     superuser=True)
     user.save().run_sync()
     SessionsBase.create_session_sync(user_id=user.id)
Ejemplo n.º 2
0
def create():
    """
    Create a new user.
    """
    username = get_username()
    email = get_email()
    password = get_password()
    confirmed_password = get_confirmed_password()

    if not password == confirmed_password:
        sys.exit("Passwords don't match!")

    if len(password) < 4:
        sys.exit("The password is too short")

    is_admin = get_is_admin()
    is_superuser = get_is_superuser()
    is_active = get_is_active()

    user = BaseUser(
        username=username,
        password=password,
        admin=is_admin,
        email=email,
        active=is_active,
        superuser=is_superuser,
    )
    user.save().run_sync()

    print(f"Created User {user.id}")
Ejemplo n.º 3
0
    def test_update_password(self):
        username = "******"
        password = "******"
        email = "*****@*****.**"

        user = BaseUser(username=username, password=password, email=email)
        user.save().run_sync()

        authenticated = BaseUser.login_sync(username, password)
        self.assertTrue(authenticated is not None)

        # Test success
        new_password = "******"
        BaseUser.update_password_sync(username, new_password)
        authenticated = BaseUser.login_sync(username, new_password)
        self.assertTrue(authenticated is not None)

        # Test ultra long password
        malicious_password = secrets.token_urlsafe(1000)
        with self.assertRaises(ValueError) as manager:
            BaseUser.update_password_sync(username, malicious_password)
        self.assertEqual(
            manager.exception.__str__(),
            "The password is too long.",
        )
Ejemplo n.º 4
0
    def test_login_success(self):
        user = BaseUser(**self.credentials)
        user.save().run_sync()

        client = TestClient(APP)
        response = client.post("/", json=self.credentials)

        self.assertTrue(response.status_code == 200)
        self.assertTrue("token" in response.json())
Ejemplo n.º 5
0
    def test_long_password_error(self):
        with self.assertRaises(ValueError) as manager:
            BaseUser.create_user_sync(
                username="******",
                password="******" * (BaseUser._max_password_length + 1),
            )

        self.assertEqual(manager.exception.__str__(),
                         "The password is too long.")
Ejemplo n.º 6
0
    def test_secret(self):
        """
        Make sure that secret fields are omitted from the response when
        requested.
        """
        user = BaseUser(username="******", password="******")
        user.save().run_sync()

        user_dict = BaseUser.select(exclude_secrets=True).first().run_sync()
        self.assertTrue("password" not in user_dict.keys())
Ejemplo n.º 7
0
    def test_create(self, *args, **kwargs):
        user = BaseUser(username="******", password="******")
        user.save().run_sync()

        change_password()

        self.assertTrue(
            BaseUser.login_sync(username="******", password="******")
            is not None
        )
Ejemplo n.º 8
0
    def test_login_success(self):
        user = BaseUser(**self.credentials)
        user.save().run_sync()

        token = TokenAuth.create_token_sync(user_id=user.id)

        client = TestClient(APP)
        response = client.post("/", json=self.credentials)

        self.assertTrue(response.status_code == 200)
        self.assertTrue(response.json()["token"] == token)
Ejemplo n.º 9
0
    def test_sucess(self):
        provider = PiccoloTokenAuthProvider()

        user = BaseUser(**self.credentials)
        user.save().run_sync()

        token = TokenAuth.create_token_sync(user_id=user.id)

        queried_user = run_sync(provider.get_user(token))

        self.assertEqual(user.username, queried_user.user["username"])
Ejemplo n.º 10
0
    def test_login_failure(self):
        user = BaseUser(**self.credentials)
        user.save().run_sync()

        client = TestClient(APP)
        with self.assertRaises(HTTPException):
            response = client.post("/",
                                   json={
                                       "username": "******",
                                       "password": "******"
                                   })
            self.assertTrue(response.status_code == 401)
Ejemplo n.º 11
0
    def setUp(self):
        BaseUser.create_table(if_not_exists=True).run_sync()

        BaseUser(
            username="******",
            password="******",
            first_name="Bob",
            last_name="Jones",
            email="*****@*****.**",
            active=False,
            admin=False,
            superuser=False,
        ).save().run_sync()
Ejemplo n.º 12
0
    def test_login(self, logger: MagicMock):
        username = "******"
        password = "******"
        email = "*****@*****.**"

        user = BaseUser(username=username, password=password, email=email)
        user.save().run_sync()

        # Test correct password
        authenticated = BaseUser.login_sync(username, password)
        self.assertTrue(authenticated == user.id)

        # Test incorrect password
        authenticated = BaseUser.login_sync(username, "blablabla")
        self.assertTrue(authenticated is None)

        # Test ultra long password
        malicious_password = secrets.token_urlsafe(1000)
        authenticated = BaseUser.login_sync(username, malicious_password)
        self.assertTrue(authenticated is None)
        self.assertEqual(
            logger.method_calls,
            [call.warning("Excessively long password provided.")],
        )

        # Test ulta long username
        logger.reset_mock()
        malicious_username = secrets.token_urlsafe(1000)
        authenticated = BaseUser.login_sync(malicious_username, password)
        self.assertTrue(authenticated is None)
        self.assertEqual(
            logger.method_calls,
            [call.warning("Excessively long username provided.")],
        )
Ejemplo n.º 13
0
    def test_hashed_password_error(self, logger: MagicMock):
        with self.assertRaises(ValueError) as manager:
            BaseUser.create_user_sync(username="******",
                                      password="******")

        self.assertEqual(manager.exception.__str__(),
                         "Do not pass a hashed password.")
        self.assertEqual(
            logger.method_calls,
            [
                call.warning(
                    "Tried to create a user with an already hashed password.")
            ],
        )
Ejemplo n.º 14
0
    def test_create_user_table(self):
        """
        Make sure the table can be created.
        """
        exception = None
        try:
            BaseUser.create_table().run_sync()
        except Exception as e:
            exception = e
        else:
            BaseUser.alter().drop_table().run_sync()

        if exception:
            raise exception

        self.assertFalse(exception)
Ejemplo n.º 15
0
    def test_login(self):
        username = "******"
        password = "******"
        email = "*****@*****.**"

        user = BaseUser(username=username, password=password, email=email)

        save_query = user.save()

        save_query.run_sync()

        authenticated = asyncio.run(BaseUser.login(username, password))
        self.assertTrue(authenticated is not None)

        authenticated = asyncio.run(BaseUser.login(username, "blablabla"))
        self.assertTrue(not authenticated)
Ejemplo n.º 16
0
def create(
    username: t.Optional[str] = None,
    email: t.Optional[str] = None,
    password: t.Optional[str] = None,
    is_admin: t.Optional[bool] = None,
    is_superuser: t.Optional[bool] = None,
    is_active: t.Optional[bool] = None,
):
    """
    Create a new user.
    """
    username = get_username() if username is None else username
    email = get_email() if email is None else email
    if password is None:
        password = get_password()
        confirmed_password = get_confirmed_password()

        if password != confirmed_password:
            sys.exit("Passwords don't match!")

    is_admin = get_is_admin() if is_admin is None else is_admin
    is_superuser = get_is_superuser() if is_superuser is None else is_superuser
    is_active = get_is_active() if is_active is None else is_active

    user = BaseUser.create_user_sync(
        username=username,
        password=password,
        admin=is_admin,
        email=email,
        active=is_active,
        superuser=is_superuser,
    )

    print(f"Created User {user.id}")
Ejemplo n.º 17
0
    def test_create(self, *args, **kwargs):
        create()

        self.assertTrue(BaseUser.exists().where(
            (BaseUser.admin == True)  # noqa: E712
            & (BaseUser.username == "bob123")
            & (BaseUser.email == "*****@*****.**")).run_sync())
Ejemplo n.º 18
0
 def test_create_user_from_fixture(self):
     the_data = {
         "id":
         2,
         "username":
         "",
         "password":
         "******"
         "446b93ed5b$c862974665ccc25b334ed42fa7e96a41"
         "04d5ddff0c2e56e0e5b1d0efc67e9d03",
         "first_name":
         "",
         "last_name":
         "",
         "email":
         "",
         "active":
         False,
         "admin":
         False,
         "superuser":
         False,
         "last_login":
         None,
     }
     user = BaseUser.from_dict(the_data)
     self.assertIsInstance(user, BaseUser)
     self.assertEqual(user.password, the_data["password"])
Ejemplo n.º 19
0
def change_password():
    """
    Change a user's password.
    """
    username = get_username()
    password = get_password()
    confirmed_password = get_confirmed_password()

    if not password == confirmed_password:
        sys.exit("Passwords don't match!")

    BaseUser.update_password_sync(user=username, password=password)

    print(f"Updated password for {username}")
    print(
        "If using session auth, we recommend invalidating this user's session."
    )
Ejemplo n.º 20
0
async def register_user(user: UserModelIn):
    user = BaseUser(**user.__dict__)
    if (await BaseUser.exists().where(BaseUser.email == user.email).run()
            or await BaseUser.exists().where(BaseUser.username == user.username
                                             ).run()):
        raise HTTPException(
            status_code=status.HTTP_422_UNPROCESSABLE_ENTITY,
            detail="User with that email or username already exists.",
        )
    await user.save().run()
    return UserModelOut(**user.__dict__)
Ejemplo n.º 21
0
 def get(self, request):
     data = (SessionsBase.select(SessionsBase.user_id).where(
         SessionsBase.token == request.cookies.get(
             "id")).first().run_sync())
     if data:
         session_user = (BaseUser.select(
             BaseUser.username).where(BaseUser._meta.primary_key ==
                                      data["user_id"]).first().run_sync())
         return PlainTextResponse(f"hello {session_user['username']}")
     else:
         return PlainTextResponse("hello world")
Ejemplo n.º 22
0
 def test_register_user_already_exist(self):
     """
     Check that a user who already exists cannot register.
     """
     client = TestClient(APP)
     BaseUser(
         username="******", email="*****@*****.**", password="******"
     ).save().run_sync()
     response = client.post("/register/", json=self.register_credentials)
     self.assertEqual(response.status_code, 422)
     self.assertEqual(
         response.content, b"User with email or username already exists."
     )
Ejemplo n.º 23
0
    def test_update_password(self):
        username = "******"
        password = "******"
        email = "*****@*****.**"

        user = BaseUser(username=username, password=password, email=email)
        user.save().run_sync()

        authenticated = BaseUser.login_sync(username, password)
        self.assertTrue(authenticated is not None)

        new_password = "******"
        BaseUser.update_password_sync(username, new_password)
        authenticated = BaseUser.login_sync(username, new_password)
        self.assertTrue(authenticated is not None)
Ejemplo n.º 24
0
    def test_non_admin(self):
        """
        Non-admin users should be rejected by the middleware, if configured
        that way.
        """
        client = TestClient(APP)
        BaseUser(**self.credentials, active=True, admin=False,
                 superuser=False).save().run_sync()
        response = client.post("/login/", json=self.credentials)
        self.assertTrue(response.status_code == 303)

        # Make a request using the session - it should get rejected.
        response = client.get("/secret/")
        self.assertTrue(response.status_code == 400)
        self.assertEqual(response.content, b"Admin users only")
Ejemplo n.º 25
0
    def test_login_success(self):
        """
        Make sure a user with the correct permissions can access the protected
        endpoint.
        """
        client = TestClient(APP)
        BaseUser(**self.credentials, active=True, admin=True,
                 superuser=True).save().run_sync()
        response = client.post("/login/", json=self.credentials)
        self.assertTrue(response.status_code == 303)
        self.assertTrue("id" in response.cookies.keys())

        response = client.get("/secret/")
        self.assertTrue(response.status_code == 200)
        self.assertEqual(response.content, b"top secret")
Ejemplo n.º 26
0
    def test_hooks(self):
        # TODO Replace these with mocks ...
        def pre_login_test(username):
            assert isinstance(username, str)

        async def pre_login_test_async(username):
            assert isinstance(username, str)

        def login_success_test(username, user_id):
            assert isinstance(username, str)
            assert isinstance(user_id, int)

        async def login_success_test_async(username, user_id):
            assert isinstance(username, str)
            assert isinstance(user_id, int)

        def login_failure_test(username):
            assert isinstance(username, str)

        def login_failure_test_async(username):
            assert isinstance(username, str)

        router = Router(
            routes=[
                Route(
                    "/login/",
                    session_login(
                        hooks=LoginHooks(
                            pre_login=[pre_login_test, pre_login_test_async],
                            login_success=[
                                login_success_test,
                                login_success_test_async,
                            ],
                            login_failure=[
                                login_failure_test,
                                login_failure_test_async,
                            ],
                        )
                    ),
                ),
            ]
        )
        app = ExceptionMiddleware(router)

        BaseUser(**self.credentials, active=True).save().run_sync()

        client = TestClient(app)
        client.post("/login/", json=self.credentials)
Ejemplo n.º 27
0
    def test_create_with_arguments(self, *args, **kwargs):
        arguments = {
            "username": "******",
            "email": "*****@*****.**",
            "password": "******",
            "is_admin": True,
            "is_superuser": True,
            "is_active": True,
        }
        create(**arguments)

        self.assertTrue(
            BaseUser.exists().where((BaseUser.admin == True)  # noqa: E712
                                    & (BaseUser.username == "bob123")
                                    & (BaseUser.email == "*****@*****.**")
                                    & (BaseUser.superuser.eq(True))
                                    & (BaseUser.active.eq(True))).run_sync())
Ejemplo n.º 28
0
    def test_inactive_user(self):
        """
        Inactive users should be rejected by the middleware, if configured
        that way.
        """
        client = TestClient(APP)
        BaseUser(**self.credentials, active=False, admin=True,
                 superuser=True).save().run_sync()
        response = client.post("/login/", json=self.credentials)

        # Currently the login is successful if the user is inactive - this
        # should change in the future.
        self.assertTrue(response.status_code == 303)

        # Make a request using the session - it should get rejected.
        response = client.get("/secret/")
        self.assertTrue(response.status_code == 400)
        self.assertEqual(response.content, b"Active users only")
Ejemplo n.º 29
0
    def test_change_password_missing_fields(self):
        """
        Make sure all fields on the form are filled out.
        """
        client = TestClient(APP)
        BaseUser(
            **self.credentials, active=True, admin=True, superuser=True
        ).save().run_sync()
        response = client.post("/login/", json=self.credentials)

        client = TestClient(APP)
        response = client.post(
            "/change-password/",
            cookies={"id": f"{response.cookies.values()[0]}"},
            json={},
        )
        self.assertEqual(response.status_code, 422)
        self.assertEqual(
            response.content, b"Form is invalid. Missing one or more fields."
        )
Ejemplo n.º 30
0
    def test_correct_current_password(self):
        """
        Make sure a POST request to `change_password` works.
        """
        client = TestClient(APP)
        BaseUser(
            **self.credentials, active=True, admin=True, superuser=True
        ).save().run_sync()
        response = client.post("/login/", json=self.credentials)

        client = TestClient(APP)
        response = client.post(
            "/change-password/",
            cookies={"id": f"{response.cookies.values()[0]}"},
            json={
                "current_password": f"{self.credentials['password']}",
                "new_password": "******",
                "confirm_new_password": "******",
            },
        )
        self.assertEqual(response.status_code, 303)