Example #1
0
    def test_400_if_previous_state_not_send(self, mocked_facade):
        data = {'updated': SINGLE_EXPENSE.copy()}

        raw_resp = self.put(url=endpoint, data=data)
        self.assertEqual(400, raw_resp.status_code)
        self.assertIn(ApiError.PREVIOUS_STATE_OF_EXP_MISSING,
                      raw_resp.get_data(as_text=True))
Example #2
0
    def test_normal_usage(self, mocked_db):
        mocked_db.persist.return_value = SINGLE_EXPENSE
        to_persist = SINGLE_EXPENSE.copy()
        to_persist['id'] = None
        raw_resp = self.post(url=endpoint, data=to_persist)
        self.assertEqual(200, raw_resp.status_code)

        self.assertTrue(mocked_db.persist.called, "persist should have been called")
        args, kwargs = mocked_db.persist.call_args
        self.assertDictEqual(kwargs, {"expense": to_persist, "user_uid": self.firebase_uid})
Example #3
0
 def test_normal_usage(self, mocked_db: type(db_facade)):
     mocked_db.remove.return_value = True
     exp = SINGLE_EXPENSE.copy()
     self.post(url=endpoint, data=exp)
     self.assertTrue(mocked_db.remove.called)
     call_args, call_kwargs = mocked_db.remove.call_args
     self.assertDictEqual({
         'expense': exp,
         'user_uid': self.firebase_uid
     }, call_kwargs)
Example #4
0
def generate_expenses(size):
    items = []
    now = dt.now(timezone.utc)
    exp = SINGLE_EXPENSE.copy()
    for i in range(size):
        temp = exp.copy()
        temp['id'] = str(i)
        temp['timestamp_utc'] = temp[
            'timestamp_utc_updated'] = ensure_ts_str_ends_with_z(
                (now - td(seconds=i)).isoformat())
        items.append(temp)
    return items
Example #5
0
    def test_invalid_expense(self):
        invalid_expenses = []

        invalid_expense_1 = SINGLE_EXPENSE.copy()
        del invalid_expense_1['timestamp_utc']
        invalid_expense_1['id'] = None
        invalid_expenses.append(invalid_expense_1)

        for invalid_expense in invalid_expenses:
            func_kwargs = {
                "expense": invalid_expense,
                "user_uid": self.firebase_uid
            }
            should_boom = self.facade.persist

            self.assertRaises(PersistFailed, should_boom, **func_kwargs)
Example #6
0
    def test_errors_on_no_such_expense(self):
        """
        remove() should raise an exception in either cases:
        * an expense with the same SORT key attribute doesn't exist
        * an expense with the same `id` attribute doesn't exist
        """
        assert self.expenses_table.item_count
        exp = SINGLE_EXPENSE.copy()
        non_persisted_expenses = [{
            **exp, 'id': 'boom'
        }, {
            **exp, 'timestamp_utc': utc_now_str()
        }]

        for e in non_persisted_expenses:
            self.assertRaises(NoExpenseWithThisId, self.facade.remove, e,
                              self.firebase_uid)
Example #7
0
    def test_normal_usage(self):
        expense_to_persist = SINGLE_EXPENSE.copy()
        expense_to_persist['id'] = None

        persisted = self.facade.persist(expense_to_persist,
                                        user_uid=self.firebase_uid)
        self.assertTrue(Validator.validate_expense_simple(persisted))

        self.assertIsNotNone(persisted['id'])
        self.assertNotEqual(
            expense_to_persist['timestamp_utc_created'],
            persisted['timestamp_utc_created'],
            "When an expense is created, its created_at must be set by the server right before persisting"
        )

        raw_persisted_expense = self.expenses_table.get_item(
            Key={
                'timestamp_utc': persisted['timestamp_utc'],
                'user_uid': self.firebase_uid
            },
            ConsistentRead=True)['Item']

        self.assertEqual(raw_persisted_expense['id'], persisted['id'])
Example #8
0
from tests.test_expenses_api import db_facade_path

from json import loads
from unittest.mock import patch

from app.expenses_api.api_error_msgs import ApiError
from tests.base_test import BaseTest, BaseTestWithHTTPMethodsMixin, NoAuthenticationMarkerMixin
from tests.common_methods import SINGLE_EXPENSE, Validator

endpoint = 'expenses_api.persist'
valid_payload = {
    **SINGLE_EXPENSE.copy(), "id": None
}


class TestPersistAuth(BaseTest, BaseTestWithHTTPMethodsMixin):
    def test_auth(self):
        resp = self.post(url=endpoint, data=valid_payload)
        self.assertEqual(403, resp.status_code)


@patch(db_facade_path, autospec=True)
class TestPersist(BaseTest, BaseTestWithHTTPMethodsMixin, NoAuthenticationMarkerMixin):

    def test_normal_usage(self, mocked_db):
        mocked_db.persist.return_value = SINGLE_EXPENSE

        to_persist = valid_payload.copy()
        raw_resp = self.post(url=endpoint, data=to_persist)
        self.assertEqual(200, raw_resp.status_code)
Example #9
0
from tests.base_test import BaseTestWithHTTPMethodsMixin, BaseTest, NoAuthenticationMarkerMixin

from json import loads
from unittest.mock import patch

from app.db_facade.facade import NoExpenseWithThisId
from app.expenses_api.api_error_msgs import ApiError
from app.models.expense_validation import Validator
from tests.common_methods import SINGLE_EXPENSE
from tests.test_expenses_api import db_facade_path

endpoint = 'expenses_api.update'
valid_payload = {
    'updated': SINGLE_EXPENSE.copy(),
    'previous_state': SINGLE_EXPENSE.copy()
}


class TestUpdateAuth(BaseTest, BaseTestWithHTTPMethodsMixin):
    def test_update(self):
        resp = self.put(url=endpoint, data=valid_payload)
        self.assertEqual(403, resp.status_code)


@patch(db_facade_path, autospec=True)
class TestUpdate(BaseTestWithHTTPMethodsMixin, BaseTest,
                 NoAuthenticationMarkerMixin):
    def test_normal_usage(self, mocked_facade):
        mocked_facade.update.return_value = SINGLE_EXPENSE
        updated = valid_payload['updated'].copy()
Example #10
0
 def test_deep_equal(self):
     copy = SINGLE_EXPENSE.copy()
     copy['id'] = 1000
     copy2 = SINGLE_EXPENSE.copy()
     copy2['id'] = 1000
     self.assertEqual([copy, 'asd'], [copy2, 'asd'])
Example #11
0
from tests.base_test import BaseTest, BaseTestWithHTTPMethodsMixin, NoAuthenticationMarkerMixin

from unittest.mock import patch
from app.db_facade.facade import NoExpenseWithThisId
from app.expenses_api.views import db_facade
from app.expenses_api.api_error_msgs import ApiError
from app.models.sample_expenses import sample_expenses
from tests.common_methods import SINGLE_EXPENSE
from tests.test_expenses_api import db_facade_path

endpoint = 'expenses_api.remove'
valid_payload = SINGLE_EXPENSE.copy()


class TestDeleteAuth(BaseTest, BaseTestWithHTTPMethodsMixin):
    def test_auth(self):
        resp = self.post(url=endpoint, data=valid_payload.copy())
        self.assertEqual(403, resp.status_code)


@patch(db_facade_path, autospec=True)
class TestRemove(BaseTest, BaseTestWithHTTPMethodsMixin, NoAuthenticationMarkerMixin):

    def test_normal_usage(self, mocked_db):
        mocked_db.remove.return_value = None

        raw_resp = self.post(url=endpoint, data=valid_payload)

        self.assertTrue(mocked_db.remove.called)
        self.assertEqual(200, raw_resp.status_code)