示例#1
0
def test_user_transfer(superadmin_client):
    user = UserFactory.create()
    EmploymentFactory.create(user=user,
                             start_date=date(2017, 12, 28),
                             percentage=100)
    AbsenceTypeFactory.create(fill_worktime=True)
    AbsenceTypeFactory.create(fill_worktime=False)
    absence_type = AbsenceTypeFactory.create(fill_worktime=False)
    AbsenceFactory.create(user=user,
                          type=absence_type,
                          date=date(2017, 12, 29))

    url = reverse('user-transfer', args=[user.id])
    response = superadmin_client.post(url)
    assert response.status_code == status.HTTP_204_NO_CONTENT

    # running transfer twice should lead to same result
    response = superadmin_client.post(url)
    assert response.status_code == status.HTTP_204_NO_CONTENT

    assert user.overtime_credits.count() == 1
    overtime_credit = user.overtime_credits.first()
    assert overtime_credit.transfer
    assert overtime_credit.date == date(2018, 1, 1)
    assert overtime_credit.duration == timedelta(hours=-8, minutes=-30)
    assert overtime_credit.comment == 'Transfer 2017'

    assert user.absence_credits.count() == 1
    absence_credit = user.absence_credits.first()
    assert absence_credit.transfer
    assert absence_credit.date == date(2018, 1, 1)
    assert absence_credit.days == -1
    assert absence_credit.comment == 'Transfer 2017'
示例#2
0
def test_worktime_balance_with_employments(auth_client,
                                           django_assert_num_queries):
    # Calculate over one week
    start_date = date(2017, 3, 19)
    end_date = date(2017, 3, 26)

    employment = EmploymentFactory.create(user=auth_client.user,
                                          start_date=start_date,
                                          worktime_per_day=timedelta(
                                              hours=8, minutes=30),
                                          end_date=date(2017, 3, 23))
    EmploymentFactory.create(user=auth_client.user,
                             start_date=date(2017, 3, 24),
                             worktime_per_day=timedelta(hours=8),
                             end_date=None)

    # Overtime credit of 10 hours
    OvertimeCreditFactory.create(user=auth_client.user,
                                 date=start_date,
                                 duration=timedelta(hours=10, minutes=30))

    # One public holiday during workdays
    PublicHolidayFactory.create(date=start_date, location=employment.location)
    # One public holiday on weekend
    PublicHolidayFactory.create(date=start_date + timedelta(days=1),
                                location=employment.location)

    # 2x 10 hour reported worktime
    ReportFactory.create(user=auth_client.user,
                         date=start_date + timedelta(days=3),
                         duration=timedelta(hours=10))

    ReportFactory.create(user=auth_client.user,
                         date=start_date + timedelta(days=4),
                         duration=timedelta(hours=10))

    # one absence
    AbsenceFactory.create(user=auth_client.user,
                          date=start_date + timedelta(days=5))

    url = reverse('worktime-balance-detail',
                  args=[
                      '{0}_{1}'.format(auth_client.user.id,
                                       end_date.strftime('%Y-%m-%d'))
                  ])

    with django_assert_num_queries(12):
        result = auth_client.get(url)
    assert result.status_code == status.HTTP_200_OK

    # 4 workdays 8.5 hours, 1 workday 8 hours, minus one holiday 8.5
    # minutes 10.5 hours overtime credit
    expected_worktime = timedelta(hours=23)

    # 2 x 10 reports hours + 1 absence of 8 hours
    expected_reported = timedelta(hours=28)

    json = result.json()
    assert json['data']['attributes']['balance'] == (
        duration_string(expected_reported - expected_worktime))
    def test_absence_credit_balance(self):
        """Should calculate an absence credit balance."""
        absence_credit = AbsenceCreditFactory.create(
            user=self.user, duration=timedelta(hours=30))

        EmploymentFactory.create(user=self.user,
                                 start_date=absence_credit.date -
                                 timedelta(days=1),
                                 worktime_per_day=timedelta(hours=8))

        AbsenceFactory.create(user=self.user,
                              type=absence_credit.absence_type,
                              date=absence_credit.date + timedelta(days=1))

        AbsenceFactory.create(user=self.user,
                              type=absence_credit.absence_type,
                              date=absence_credit.date - timedelta(days=1),
                              duration=timedelta(hours=8))

        url = reverse('absence-credit-detail', args=[absence_credit.id])

        res = self.client.get(url)
        result = self.result(res)

        assert result['data']['attributes']['duration'] == '1 06:00:00'
        assert result['data']['attributes']['used'] == '08:00:00'
        assert result['data']['attributes']['balance'] == '22:00:00'
示例#4
0
    def test_user_worktime_balance(self):
        """Should calculate correct worktime balances."""
        user = self.user
        employment = user.employments.get(end_date__isnull=True)

        # Calculate over one week
        start_date = date(2017, 3, 19)
        end_date = date(2017, 3, 26)

        employment.start_date = start_date
        employment.worktime_per_day = timedelta(hours=8)

        employment.save()

        # Overtime credit of 10 hours
        OvertimeCreditFactory.create(user=user,
                                     date=start_date,
                                     duration=timedelta(hours=10, minutes=30))

        # One public holiday during workdays
        PublicHolidayFactory.create(date=start_date,
                                    location=employment.location)
        # One public holiday on weekend
        PublicHolidayFactory.create(date=start_date + timedelta(days=1),
                                    location=employment.location)

        url = reverse('user-detail', args=[user.id])

        res = self.client.get('{0}?until={1}'.format(
            url, end_date.strftime('%Y-%m-%d')))

        result = self.result(res)

        # 5 workdays minus one holiday minus 10 hours overtime credit
        expected_worktime = (4 * employment.worktime_per_day -
                             timedelta(hours=10, minutes=30))

        assert (result['data']['attributes']['worktime-balance'] ==
                duration_string(timedelta() - expected_worktime))

        # 2x 10 hour reported worktime
        ReportFactory.create(user=user,
                             date=start_date + timedelta(days=3),
                             duration=timedelta(hours=10))

        ReportFactory.create(user=user,
                             date=start_date + timedelta(days=4),
                             duration=timedelta(hours=10))

        AbsenceFactory.create(user=user, date=start_date + timedelta(days=5))

        res2 = self.client.get('{0}?until={1}'.format(
            url, end_date.strftime('%Y-%m-%d')))

        result2 = self.result(res2)

        assert (result2['data']['attributes']['worktime-balance'] ==
                duration_string(timedelta(hours=28) - expected_worktime))
示例#5
0
def test_absence_list_superuser(superadmin_client):
    AbsenceFactory.create_batch(2)

    url = reverse("absence-list")
    response = superadmin_client.get(url)
    assert response.status_code == status.HTTP_200_OK

    json = response.json()
    assert len(json["data"]) == 2
示例#6
0
    def setUp(self):
        """Set the environment for the tests up."""
        super().setUp()

        user = self.user

        other_user = User.objects.create_user(username='******',
                                              password='******')

        EmploymentFactory.create(user=user,
                                 start_date=datetime.date(2017, 5, 1),
                                 end_date=None)

        EmploymentFactory.create(user=other_user,
                                 start_date=datetime.date(2017, 5, 1),
                                 end_date=None)

        self.absences = [
            AbsenceFactory.create(user=user, date=datetime.date(2017, 5, 1)),
            AbsenceFactory.create(user=user, date=datetime.date(2017, 5, 2)),
            AbsenceFactory.create(user=user, date=datetime.date(2017, 5, 3))
        ]

        AbsenceFactory.create(user=other_user, date=datetime.date(2017, 5, 1))
        AbsenceFactory.create(user=other_user, date=datetime.date(2017, 5, 2))
        AbsenceFactory.create(user=other_user, date=datetime.date(2017, 5, 3))
示例#7
0
def test_absence_list_supervisor(auth_client):
    user = UserFactory.create()
    auth_client.user.supervisees.add(user)

    AbsenceFactory.create(user=auth_client.user)
    AbsenceFactory.create(user=user)

    url = reverse("absence-list")
    response = auth_client.get(url)
    assert response.status_code == status.HTTP_200_OK
    json = response.json()
    assert len(json["data"]) == 2
示例#8
0
    def test_user_absence_types_fill_worktime(self):
        absence_type = AbsenceTypeFactory.create(fill_worktime=True)

        employment = self.user.employments.get(end_date__isnull=True)

        employment.worktime_per_day = timedelta(hours=5)
        employment.start_date       = date.today() - timedelta(days=1)

        employment.save()

        ReportFactory.create(
            user=self.user,
            date=date.today(),
            duration=timedelta(hours=4)
        )

        AbsenceFactory.create(date=date.today(),
                              user=self.user,
                              type=absence_type)

        AbsenceFactory.create(date=date.today() - timedelta(days=1),
                              user=self.user,
                              type=absence_type)

        url = reverse('user-detail', args=[
            self.user.id
        ])

        res = self.client.get(url, {'include': 'user_absence_types'})

        assert res.status_code == HTTP_200_OK

        result = self.result(res)

        rel = result['data']['relationships']
        inc = result['included']

        assert len(rel['user-absence-types']['data']) == 1
        assert len(inc) == 1

        assert (
            inc[0]['id'] ==
            '{0}-{1}'.format(self.user.id, absence_type.id)
        )

        assert inc[0]['attributes']['credit'] is None
        assert inc[0]['attributes']['balance'] is None
        assert inc[0]['attributes']['used-days'] is None
        assert inc[0]['attributes']['used-duration'] == '06:00:00'
示例#9
0
def test_absence_update_owner(auth_client):
    user = auth_client.user
    date = datetime.date(2017, 5, 3)
    absence = AbsenceFactory.create(
        user=auth_client.user, date=datetime.date(2016, 5, 3)
    )
    EmploymentFactory.create(
        user=user, start_date=date, worktime_per_day=datetime.timedelta(hours=8)
    )

    data = {
        "data": {
            "type": "absences",
            "id": absence.id,
            "attributes": {"date": date.strftime("%Y-%m-%d")},
        }
    }

    url = reverse("absence-detail", args=[absence.id])

    response = auth_client.patch(url, data)

    assert response.status_code == status.HTTP_200_OK
    json = response.json()
    assert json["data"]["attributes"]["date"] == "2017-05-03"
示例#10
0
def test_absence_delete_owner(auth_client):
    absence = AbsenceFactory.create(user=auth_client.user)

    url = reverse("absence-detail", args=[absence.id])

    response = auth_client.delete(url)
    assert response.status_code == status.HTTP_204_NO_CONTENT
示例#11
0
def test_absence_delete_superuser(superadmin_client):
    """Test that superuser may not delete absences of other users."""
    user = UserFactory.create()
    absence = AbsenceFactory.create(user=user)

    url = reverse("absence-detail", args=[absence.id])

    response = superadmin_client.delete(url)
    assert response.status_code == status.HTTP_403_FORBIDDEN
示例#12
0
def test_absence_balance_full_day(auth_client, django_assert_num_queries):
    day = date(2017, 2, 28)

    user = auth_client.user
    EmploymentFactory.create(user=user, start_date=day)
    absence_type = AbsenceTypeFactory.create()

    AbsenceCreditFactory.create(date=day,
                                user=user,
                                days=5,
                                absence_type=absence_type)

    # credit on different user, may not show up
    AbsenceCreditFactory.create(date=date.today(), absence_type=absence_type)

    AbsenceFactory.create(date=day, user=user, type=absence_type)

    AbsenceFactory.create(date=day - timedelta(days=1),
                          user=user,
                          type=absence_type)

    url = reverse('absence-balance-list')

    with django_assert_num_queries(7):
        result = auth_client.get(url,
                                 data={
                                     'date': '2017-03-01',
                                     'user': user.id,
                                     'include': 'absence_credits,absence_type'
                                 })

    assert result.status_code == status.HTTP_200_OK
    json = result.json()
    assert len(json['data']) == 1
    entry = json['data'][0]

    assert (entry['id'] == '{0}_{1}_2017-03-01'.format(user.id,
                                                       absence_type.id))
    assert entry['attributes']['credit'] == 5
    assert entry['attributes']['used-days'] == 2
    assert entry['attributes']['used-duration'] is None
    assert entry['attributes']['balance'] == 3

    assert len(json['included']) == 2
示例#13
0
def test_absence_detail(auth_client):
    absence = AbsenceFactory.create(user=auth_client.user)

    url = reverse("absence-detail", args=[absence.id])

    response = auth_client.get(url)

    assert response.status_code == status.HTTP_200_OK
    json = response.json()
    assert json["data"]["id"] == str(absence.id)
示例#14
0
def test_absence_detail_unemployed(auth_client):
    """Test creation of absence fails on unemployed day."""
    absence = AbsenceFactory.create(user=auth_client.user)

    url = reverse("absence-detail", args=[absence.id])

    res = auth_client.get(url)
    assert res.status_code == status.HTTP_200_OK

    json = res.json()
    assert json["data"]["attributes"]["duration"] == "00:00:00"
示例#15
0
def test_absence_list_authenticated(auth_client):
    absence = AbsenceFactory.create(user=auth_client.user)

    # overlapping absence with public holidays need to be hidden
    overlap_absence = AbsenceFactory.create(
        user=auth_client.user, date=datetime.date(2018, 1, 1)
    )
    employment = EmploymentFactory.create(
        user=overlap_absence.user, start_date=datetime.date(2017, 12, 31)
    )
    PublicHolidayFactory.create(date=overlap_absence.date, location=employment.location)
    url = reverse("absence-list")

    response = auth_client.get(url)
    assert response.status_code == status.HTTP_200_OK

    json = response.json()

    assert len(json["data"]) == 1
    assert json["data"][0]["id"] == str(absence.id)
示例#16
0
def test_absence_balance_fill_worktime(auth_client, django_assert_num_queries):
    day = date(2017, 2, 28)

    user = UserFactory.create()
    user.supervisors.add(auth_client.user)
    EmploymentFactory.create(user=user,
                             start_date=day,
                             worktime_per_day=timedelta(hours=5))
    absence_type = AbsenceTypeFactory.create(fill_worktime=True)

    ReportFactory.create(user=user,
                         date=day + timedelta(days=1),
                         duration=timedelta(hours=4))

    AbsenceFactory.create(date=day + timedelta(days=1),
                          user=user,
                          type=absence_type)

    AbsenceFactory.create(date=day, user=user, type=absence_type)

    url = reverse('absence-balance-list')
    with django_assert_num_queries(12):
        result = auth_client.get(url,
                                 data={
                                     'date': '2017-03-01',
                                     'user': user.id,
                                     'include': 'absence_credits,absence_type'
                                 })
    assert result.status_code == status.HTTP_200_OK

    json = result.json()
    assert len(json['data']) == 1
    entry = json['data'][0]

    assert (entry['id'] == '{0}_{1}_2017-03-01'.format(user.id,
                                                       absence_type.id))

    assert entry['attributes']['credit'] is None
    assert entry['attributes']['balance'] is None
    assert entry['attributes']['used-days'] is None
    assert entry['attributes']['used-duration'] == '06:00:00'
示例#17
0
    def test_user_absence_types(self):
        absence_type = AbsenceTypeFactory.create()

        credit = AbsenceCreditFactory.create(date=date.today(),
                                             user=self.user,
                                             days=5,
                                             absence_type=absence_type)

        AbsenceFactory.create(date=date.today(),
                              user=self.user,
                              type=absence_type)

        AbsenceFactory.create(date=date.today() - timedelta(days=1),
                              user=self.user,
                              type=absence_type)

        url = reverse('user-detail', args=[
            self.user.id
        ])

        res = self.client.get(url, {'include': 'user_absence_types'})

        assert res.status_code == HTTP_200_OK

        result = self.result(res)

        rel = result['data']['relationships']
        inc = result['included']

        assert len(rel['user-absence-types']['data']) == 1
        assert len(inc) == 1

        assert (
            inc[0]['id'] ==
            '{0}-{1}'.format(self.user.id, credit.absence_type.id)
        )

        assert inc[0]['attributes']['credit'] == 5
        assert inc[0]['attributes']['balance'] == 3
        assert inc[0]['attributes']['used-days'] == 2
        assert inc[0]['attributes']['used-duration'] is None
def test_absence_balance_fill_worktime(auth_client, django_assert_num_queries):
    day = date(2017, 2, 28)

    user = UserFactory.create()
    user.supervisors.add(auth_client.user)
    EmploymentFactory.create(
        user=user, start_date=day, worktime_per_day=timedelta(hours=5)
    )
    absence_type = AbsenceTypeFactory.create(fill_worktime=True)

    ReportFactory.create(
        user=user, date=day + timedelta(days=1), duration=timedelta(hours=4)
    )

    AbsenceFactory.create(date=day + timedelta(days=1), user=user, type=absence_type)

    AbsenceFactory.create(date=day, user=user, type=absence_type)

    url = reverse("absence-balance-list")
    with django_assert_num_queries(11):
        result = auth_client.get(
            url,
            data={
                "date": "2017-03-01",
                "user": user.id,
                "include": "absence_credits,absence_type",
            },
        )
    assert result.status_code == status.HTTP_200_OK

    json = result.json()
    assert len(json["data"]) == 1
    entry = json["data"][0]

    assert entry["id"] == "{0}_{1}_2017-03-01".format(user.id, absence_type.id)

    assert entry["attributes"]["credit"] is None
    assert entry["attributes"]["balance"] is None
    assert entry["attributes"]["used-days"] is None
    assert entry["attributes"]["used-duration"] == "06:00:00"
def test_absence_balance_full_day(auth_client, django_assert_num_queries):
    day = date(2017, 2, 28)

    user = auth_client.user
    EmploymentFactory.create(user=user, start_date=day)
    absence_type = AbsenceTypeFactory.create()

    AbsenceCreditFactory.create(date=day, user=user, days=5, absence_type=absence_type)

    # credit on different user, may not show up
    AbsenceCreditFactory.create(date=date.today(), absence_type=absence_type)

    AbsenceFactory.create(date=day, user=user, type=absence_type)

    AbsenceFactory.create(date=day - timedelta(days=1), user=user, type=absence_type)

    url = reverse("absence-balance-list")

    with django_assert_num_queries(6):
        result = auth_client.get(
            url,
            data={
                "date": "2017-03-01",
                "user": user.id,
                "include": "absence_credits,absence_type",
            },
        )

    assert result.status_code == status.HTTP_200_OK
    json = result.json()
    assert len(json["data"]) == 1
    entry = json["data"][0]

    assert entry["id"] == "{0}_{1}_2017-03-01".format(user.id, absence_type.id)
    assert entry["attributes"]["credit"] == 5
    assert entry["attributes"]["used-days"] == 2
    assert entry["attributes"]["used-duration"] is None
    assert entry["attributes"]["balance"] == 3

    assert len(json["included"]) == 2
示例#20
0
    def test_absence_update_on_create_report(self):
        """Should update the absence after creating a new report."""
        task = TaskFactory.create()
        type = AbsenceTypeFactory.create(fill_worktime=True)
        day = date(2017, 5, 3)

        employment = EmploymentFactory.create(user=self.user, start_date=day)

        absence = AbsenceFactory.create(user=self.user, date=day, type=type)

        Report.objects.create(user=self.user,
                              date=day,
                              task=task,
                              duration=timedelta(hours=1))

        assert (Absence.objects.get(
            pk=absence.pk).duration == employment.worktime_per_day -
                timedelta(hours=1))
示例#21
0
def test_absence_update_superadmin_date(superadmin_client):
    """Test that superadmin may not change date of absence."""
    user = UserFactory.create()
    date = datetime.date(2017, 5, 3)
    absence = AbsenceFactory.create(user=user, date=datetime.date(2016, 5, 3))
    EmploymentFactory.create(
        user=user, start_date=date, worktime_per_day=datetime.timedelta(hours=8)
    )

    data = {
        "data": {
            "type": "absences",
            "id": absence.id,
            "attributes": {"date": date.strftime("%Y-%m-%d")},
        }
    }

    url = reverse("absence-detail", args=[absence.id])

    response = superadmin_client.patch(url, data)
    assert response.status_code == status.HTTP_400_BAD_REQUEST
示例#22
0
def test_absence_list_supervisee(auth_client):
    AbsenceFactory.create(user=auth_client.user)

    supervisors = UserFactory.create_batch(2)

    supervisors[0].supervisees.add(auth_client.user)
    AbsenceFactory.create(user=supervisors[0])

    url = reverse("absence-list")

    response = auth_client.get(url)
    assert response.status_code == status.HTTP_200_OK
    json = response.json()
    assert len(json["data"]) == 1

    # absences of multiple supervisors shouldn't affect supervisee
    supervisors[1].supervisees.add(auth_client.user)
    AbsenceFactory.create(user=supervisors[1])

    response = auth_client.get(url)
    assert response.status_code == status.HTTP_200_OK
    json = response.json()
    assert len(json["data"]) == 1