2020-07-21 16:13:57 +02:00
|
|
|
import copy
|
2017-03-23 16:24:03 +01:00
|
|
|
import datetime
|
|
|
|
import json
|
|
|
|
import os
|
|
|
|
import shutil
|
|
|
|
import sys
|
|
|
|
import tempfile
|
2019-09-21 22:36:08 +02:00
|
|
|
from io import StringIO
|
2018-03-25 11:26:47 +02:00
|
|
|
from unittest import mock
|
2017-03-23 16:24:03 +01:00
|
|
|
|
|
|
|
import pytest
|
2018-11-13 20:44:51 +01:00
|
|
|
from django.contrib.auth.models import Group
|
2023-08-17 13:42:03 +02:00
|
|
|
from django.core.files.base import ContentFile
|
2018-11-13 20:44:51 +01:00
|
|
|
from django.core.management import CommandError, call_command
|
2020-10-26 18:09:53 +01:00
|
|
|
from django.test import override_settings
|
2018-03-25 11:26:47 +02:00
|
|
|
from django.utils.encoding import force_bytes
|
2017-03-23 16:24:03 +01:00
|
|
|
|
2020-03-17 13:11:49 +01:00
|
|
|
from chrono.agendas.models import (
|
|
|
|
Agenda,
|
|
|
|
AgendaImportError,
|
2020-07-16 15:12:47 +02:00
|
|
|
AgendaNotificationsSettings,
|
2020-09-15 14:05:38 +02:00
|
|
|
AgendaReminderSettings,
|
2020-07-24 15:59:49 +02:00
|
|
|
Category,
|
2020-05-15 15:47:03 +02:00
|
|
|
Desk,
|
2020-03-17 13:11:49 +01:00
|
|
|
Event,
|
2022-04-01 10:13:52 +02:00
|
|
|
EventsType,
|
2020-03-17 13:11:49 +01:00
|
|
|
MeetingType,
|
2020-05-15 15:47:03 +02:00
|
|
|
Resource,
|
2022-06-28 14:50:00 +02:00
|
|
|
SharedCustodySettings,
|
2020-03-17 13:11:49 +01:00
|
|
|
TimePeriod,
|
|
|
|
TimePeriodException,
|
2020-10-26 18:09:53 +01:00
|
|
|
TimePeriodExceptionSource,
|
2020-10-26 17:15:47 +01:00
|
|
|
UnavailabilityCalendar,
|
2021-04-01 10:01:23 +02:00
|
|
|
VirtualMember,
|
2020-03-17 13:11:49 +01:00
|
|
|
)
|
2018-05-30 08:50:00 +02:00
|
|
|
from chrono.manager.utils import import_site
|
2023-03-08 13:00:20 +01:00
|
|
|
from chrono.utils.timezone import make_aware, now
|
2017-03-23 16:24:03 +01:00
|
|
|
|
2023-08-17 13:42:03 +02:00
|
|
|
from .test_agendas import ICS_SAMPLE, ICS_SAMPLE_WITH_NO_EVENTS
|
|
|
|
|
2017-03-23 16:24:03 +01:00
|
|
|
pytestmark = pytest.mark.django_db
|
|
|
|
|
2018-05-30 08:50:00 +02:00
|
|
|
|
2017-03-23 16:24:03 +01:00
|
|
|
def get_output_of_command(command, *args, **kwargs):
|
|
|
|
old_stdout = sys.stdout
|
|
|
|
output = sys.stdout = StringIO()
|
|
|
|
call_command(command, *args, **kwargs)
|
|
|
|
sys.stdout = old_stdout
|
|
|
|
return output.getvalue()
|
|
|
|
|
2018-05-30 08:50:00 +02:00
|
|
|
|
2020-07-21 16:38:14 +02:00
|
|
|
def test_import_export(app):
|
|
|
|
agenda_events = Agenda.objects.create(label='Events Agenda', kind='events')
|
|
|
|
first_event = Event.objects.create(
|
|
|
|
agenda=agenda_events, start_datetime=make_aware(datetime.datetime(2020, 7, 21, 16, 42, 35)), places=10
|
|
|
|
)
|
|
|
|
agenda_meetings = Agenda.objects.create(label='Meetings Agenda', kind='meetings')
|
|
|
|
MeetingType.objects.create(agenda=agenda_meetings, label='Meeting Type', duration=30)
|
|
|
|
desk = Desk.objects.create(agenda=agenda_meetings, label='Desk')
|
2021-06-30 15:50:00 +02:00
|
|
|
exceptions_desk = Desk.objects.create(agenda=agenda_events, slug='_exceptions_holder')
|
2019-09-24 15:43:54 +02:00
|
|
|
|
2018-05-30 08:54:44 +02:00
|
|
|
tpx_start = make_aware(datetime.datetime(2017, 5, 22, 8, 0))
|
|
|
|
tpx_end = make_aware(datetime.datetime(2017, 5, 22, 12, 30))
|
2017-08-24 14:15:18 +02:00
|
|
|
TimePeriodException.objects.create(desk=desk, start_datetime=tpx_start, end_datetime=tpx_end)
|
2021-01-28 15:40:57 +01:00
|
|
|
TimePeriodException.objects.create(desk=exceptions_desk, start_datetime=tpx_start, end_datetime=tpx_end)
|
2022-06-07 14:13:24 +02:00
|
|
|
TimePeriod.objects.create(
|
|
|
|
desk=desk, weekday=2, start_time=tpx_start.time(), end_time=tpx_end.time(), weekday_indexes=[1, 3]
|
|
|
|
)
|
2022-10-13 15:49:11 +02:00
|
|
|
TimePeriod.objects.create(
|
|
|
|
desk=desk, date=datetime.date(2022, 10, 24), start_time=tpx_start.time(), end_time=tpx_end.time()
|
|
|
|
)
|
2021-01-28 15:40:57 +01:00
|
|
|
|
2017-03-23 16:24:03 +01:00
|
|
|
output = get_output_of_command('export_site')
|
2020-07-21 16:38:14 +02:00
|
|
|
assert len(json.loads(output)['agendas']) == 2
|
2017-03-23 16:24:03 +01:00
|
|
|
import_site(data={}, clean=True)
|
|
|
|
empty_output = get_output_of_command('export_site')
|
|
|
|
assert len(json.loads(empty_output)['agendas']) == 0
|
|
|
|
|
|
|
|
Agenda(label='test').save()
|
|
|
|
old_stdin = sys.stdin
|
|
|
|
sys.stdin = StringIO(json.dumps({}))
|
|
|
|
assert Agenda.objects.count() == 1
|
|
|
|
try:
|
|
|
|
call_command('import_site', '-', clean=True)
|
|
|
|
finally:
|
|
|
|
sys.stdin = old_stdin
|
|
|
|
assert Agenda.objects.count() == 0
|
|
|
|
|
|
|
|
with tempfile.NamedTemporaryFile() as f:
|
2018-03-25 11:26:47 +02:00
|
|
|
f.write(force_bytes(output))
|
2017-03-23 16:24:03 +01:00
|
|
|
f.flush()
|
|
|
|
call_command('import_site', f.name)
|
|
|
|
|
2020-07-21 16:38:14 +02:00
|
|
|
assert Agenda.objects.count() == 2
|
|
|
|
first_imported_event = Agenda.objects.get(label='Events Agenda').event_set.first()
|
2019-09-24 15:43:54 +02:00
|
|
|
assert first_imported_event.start_datetime == first_event.start_datetime
|
2021-01-28 15:40:57 +01:00
|
|
|
assert TimePeriodException.objects.get(desk__agenda__kind='meetings').start_datetime == tpx_start
|
|
|
|
assert TimePeriodException.objects.get(desk__agenda__kind='meetings').end_datetime == tpx_end
|
|
|
|
assert TimePeriodException.objects.get(desk__agenda__kind='events').start_datetime == tpx_start
|
|
|
|
assert TimePeriodException.objects.get(desk__agenda__kind='events').end_datetime == tpx_end
|
2022-10-13 15:49:11 +02:00
|
|
|
assert TimePeriod.objects.filter(weekday_indexes=[1, 3]).count() == 1
|
|
|
|
assert TimePeriod.objects.filter(date=datetime.date(2022, 10, 24)).count() == 1
|
2017-03-23 16:24:03 +01:00
|
|
|
|
2020-07-21 16:38:14 +02:00
|
|
|
agenda1 = Agenda.objects.get(label='Events Agenda')
|
|
|
|
agenda2 = Agenda.objects.get(label='Meetings Agenda')
|
|
|
|
event = Event(agenda=agenda1, start_datetime=now(), places=10)
|
2017-03-23 16:24:03 +01:00
|
|
|
event.save()
|
2017-09-01 15:01:07 +02:00
|
|
|
desk, _ = Desk.objects.get_or_create(agenda=agenda2, label='Desk A', slug='desk-a')
|
2018-05-30 08:50:00 +02:00
|
|
|
timeperiod = TimePeriod(
|
|
|
|
desk=desk, weekday=2, start_time=datetime.time(10, 0), end_time=datetime.time(11, 0)
|
|
|
|
)
|
2017-03-23 16:24:03 +01:00
|
|
|
timeperiod.save()
|
2017-08-24 14:15:18 +02:00
|
|
|
exception = TimePeriodException(
|
2017-12-30 15:48:48 +01:00
|
|
|
desk=desk,
|
|
|
|
start_datetime=make_aware(datetime.datetime(2017, 5, 22, 8, 0)),
|
|
|
|
end_datetime=make_aware(datetime.datetime(2017, 5, 22, 12, 30)),
|
|
|
|
)
|
2017-08-24 14:15:18 +02:00
|
|
|
exception.save()
|
2017-03-23 16:24:03 +01:00
|
|
|
|
|
|
|
import_site(json.loads(output), overwrite=True)
|
|
|
|
assert Event.objects.filter(id=event.id).count() == 0
|
2017-09-01 15:01:07 +02:00
|
|
|
assert Desk.objects.filter(slug='desk-a').count() == 0
|
2017-03-23 16:24:03 +01:00
|
|
|
assert TimePeriod.objects.filter(id=timeperiod.id).count() == 0
|
2017-08-24 14:15:18 +02:00
|
|
|
assert TimePeriodException.objects.filter(id=exception.id).count() == 0
|
2017-03-23 16:24:03 +01:00
|
|
|
|
2020-07-21 16:38:14 +02:00
|
|
|
event = Event(agenda=agenda1, start_datetime=now(), places=10)
|
2017-03-23 16:24:03 +01:00
|
|
|
event.save()
|
2020-03-06 10:50:45 +01:00
|
|
|
desk, _ = Desk.objects.get_or_create(agenda=agenda2, label='Desk A', slug='desk-a')
|
2018-05-30 08:50:00 +02:00
|
|
|
timeperiod = TimePeriod(
|
|
|
|
weekday=2, desk=desk, start_time=datetime.time(10, 0), end_time=datetime.time(11, 0)
|
|
|
|
)
|
2017-03-23 16:24:03 +01:00
|
|
|
timeperiod.save()
|
2017-08-24 14:15:18 +02:00
|
|
|
exception = TimePeriodException(
|
2017-12-30 15:48:48 +01:00
|
|
|
desk=desk,
|
|
|
|
start_datetime=make_aware(datetime.datetime(2017, 5, 22, 8, 0)),
|
|
|
|
end_datetime=make_aware(datetime.datetime(2017, 5, 22, 12, 30)),
|
|
|
|
)
|
2017-08-24 14:15:18 +02:00
|
|
|
exception.save()
|
2017-03-23 16:24:03 +01:00
|
|
|
import_site(json.loads(output), overwrite=False)
|
|
|
|
assert Event.objects.filter(id=event.id).count() == 1
|
|
|
|
assert TimePeriod.objects.filter(id=timeperiod.id).count() == 1
|
2017-08-24 14:15:18 +02:00
|
|
|
assert TimePeriodException.objects.filter(id=exception.id).count() == 1
|
2017-03-23 16:24:03 +01:00
|
|
|
|
|
|
|
import_site(data={}, if_empty=True)
|
2020-07-21 16:38:14 +02:00
|
|
|
assert Agenda.objects.count() == 2
|
2017-03-23 16:24:03 +01:00
|
|
|
|
|
|
|
import_site(data={}, clean=True)
|
|
|
|
tempdir = tempfile.mkdtemp('chrono-test')
|
|
|
|
empty_output = get_output_of_command('export_site', output=os.path.join(tempdir, 't.json'))
|
|
|
|
assert os.path.exists(os.path.join(tempdir, 't.json'))
|
|
|
|
shutil.rmtree(tempdir)
|
2018-11-13 20:44:51 +01:00
|
|
|
|
|
|
|
|
2022-03-03 16:40:26 +01:00
|
|
|
def test_import_export_bad_date_format(app):
|
|
|
|
agenda_events = Agenda.objects.create(label='Events Agenda', kind='events')
|
|
|
|
Desk.objects.create(agenda=agenda_events, slug='_exceptions_holder')
|
|
|
|
Event.objects.create(
|
|
|
|
agenda=agenda_events, start_datetime=make_aware(datetime.datetime(2020, 7, 21, 16, 42, 35)), places=10
|
|
|
|
)
|
|
|
|
|
|
|
|
output = get_output_of_command('export_site')
|
|
|
|
payload = json.loads(output)
|
|
|
|
assert len(payload['agendas']) == 1
|
|
|
|
payload['agendas'][0]['events'][0]['start_datetime'] = '20-07-21 16:42:00'
|
|
|
|
with pytest.raises(AgendaImportError) as excinfo:
|
|
|
|
import_site(payload)
|
|
|
|
assert '%s' % excinfo.value == 'Bad datetime format "20-07-21 16:42:00"'
|
|
|
|
|
|
|
|
Agenda.objects.all().delete()
|
|
|
|
agenda_meetings = Agenda.objects.create(label='Meetings Agenda', kind='meetings')
|
|
|
|
desk = Desk.objects.create(agenda=agenda_meetings, label='Desk')
|
|
|
|
tpx_start = make_aware(datetime.datetime(2017, 5, 22, 8, 0))
|
|
|
|
tpx_end = make_aware(datetime.datetime(2017, 5, 22, 12, 30))
|
|
|
|
TimePeriodException.objects.create(desk=desk, start_datetime=tpx_start, end_datetime=tpx_end)
|
|
|
|
output = get_output_of_command('export_site')
|
|
|
|
payload = json.loads(output)
|
|
|
|
assert len(payload['agendas']) == 1
|
|
|
|
payload['agendas'][0]['desks'][0]['exceptions'][0]['start_datetime'] = '17-05-22 08:00:00'
|
|
|
|
with pytest.raises(AgendaImportError) as excinfo:
|
|
|
|
import_site(payload)
|
|
|
|
assert '%s' % excinfo.value == 'Bad datetime format "17-05-22 08:00:00"'
|
|
|
|
|
|
|
|
|
2020-09-25 11:00:31 +02:00
|
|
|
def test_import_export_events_agenda_options(app):
|
|
|
|
agenda = Agenda.objects.create(
|
|
|
|
label='Foo Bar',
|
|
|
|
kind='events',
|
|
|
|
default_view='open_events',
|
2024-03-04 17:32:20 +01:00
|
|
|
anonymize_delay=42,
|
2020-09-25 11:00:31 +02:00
|
|
|
booking_form_url='{{ eservices_url }}backoffice/submission/inscription-aux-activites/',
|
2021-07-05 16:04:30 +02:00
|
|
|
minimal_booking_delay_in_working_days=True,
|
2021-07-08 09:46:33 +02:00
|
|
|
booking_user_block_template='foo bar',
|
|
|
|
booking_check_filters='foo,bar',
|
|
|
|
event_display_template='foo bar',
|
|
|
|
mark_event_checked_auto=True,
|
2024-02-22 16:36:49 +01:00
|
|
|
disable_check_update=True,
|
|
|
|
enable_check_for_future_events=True,
|
|
|
|
booking_extra_user_block_template='foobar',
|
2020-09-25 11:00:31 +02:00
|
|
|
)
|
2021-06-30 15:50:00 +02:00
|
|
|
Desk.objects.create(agenda=agenda, slug='_exceptions_holder')
|
2020-09-25 11:00:31 +02:00
|
|
|
|
|
|
|
output = get_output_of_command('export_site')
|
|
|
|
assert len(json.loads(output)['agendas']) == 1
|
|
|
|
import_site(data={}, clean=True)
|
|
|
|
|
|
|
|
with tempfile.NamedTemporaryFile() as f:
|
|
|
|
f.write(force_bytes(output))
|
|
|
|
f.flush()
|
|
|
|
call_command('import_site', f.name)
|
|
|
|
|
|
|
|
assert Agenda.objects.count() == 1
|
|
|
|
agenda = Agenda.objects.first()
|
|
|
|
assert agenda.default_view == 'open_events'
|
2024-03-04 17:32:20 +01:00
|
|
|
assert agenda.anonymize_delay == 42
|
2020-09-25 11:00:31 +02:00
|
|
|
assert agenda.booking_form_url == '{{ eservices_url }}backoffice/submission/inscription-aux-activites/'
|
2021-07-05 16:04:30 +02:00
|
|
|
assert agenda.minimal_booking_delay_in_working_days is True
|
2021-07-08 09:46:33 +02:00
|
|
|
assert agenda.booking_user_block_template == 'foo bar'
|
|
|
|
assert agenda.booking_check_filters == 'foo,bar'
|
|
|
|
assert agenda.event_display_template == 'foo bar'
|
|
|
|
assert agenda.mark_event_checked_auto is True
|
2024-02-22 16:36:49 +01:00
|
|
|
assert agenda.disable_check_update is True
|
|
|
|
assert agenda.enable_check_for_future_events is True
|
|
|
|
assert agenda.booking_extra_user_block_template == 'foobar'
|
|
|
|
|
|
|
|
agenda.partial_bookings = True
|
|
|
|
agenda.invoicing_tolerance = 5
|
|
|
|
agenda.invoicing_unit = 'minute'
|
|
|
|
agenda.save()
|
|
|
|
|
|
|
|
output = get_output_of_command('export_site')
|
|
|
|
assert len(json.loads(output)['agendas']) == 1
|
|
|
|
import_site(data={}, clean=True)
|
|
|
|
|
|
|
|
with tempfile.NamedTemporaryFile() as f:
|
|
|
|
f.write(force_bytes(output))
|
|
|
|
f.flush()
|
|
|
|
call_command('import_site', f.name)
|
|
|
|
|
|
|
|
assert Agenda.objects.count() == 1
|
|
|
|
agenda = Agenda.objects.first()
|
|
|
|
|
|
|
|
assert agenda.partial_bookings is True
|
|
|
|
assert agenda.invoicing_tolerance == 5
|
|
|
|
assert agenda.invoicing_unit == 'minute'
|
2020-09-25 11:00:31 +02:00
|
|
|
|
|
|
|
|
2020-07-21 16:38:14 +02:00
|
|
|
def test_import_export_event_details(app):
|
|
|
|
agenda = Agenda.objects.create(label='Foo Bar', kind='events')
|
2021-06-30 15:50:00 +02:00
|
|
|
Desk.objects.create(agenda=agenda, slug='_exceptions_holder')
|
2020-07-21 16:38:14 +02:00
|
|
|
Event.objects.create(
|
2021-05-11 14:20:14 +02:00
|
|
|
slug='event',
|
2020-07-21 16:38:14 +02:00
|
|
|
agenda=agenda,
|
|
|
|
description='description',
|
|
|
|
pricing='100',
|
|
|
|
url='https://example.net/',
|
2021-10-08 15:48:14 +02:00
|
|
|
publication_datetime=make_aware(datetime.datetime(2020, 5, 11)),
|
2020-07-21 16:38:14 +02:00
|
|
|
places=42,
|
|
|
|
start_datetime=now(),
|
2021-09-08 12:24:15 +02:00
|
|
|
duration=30,
|
2020-07-21 16:38:14 +02:00
|
|
|
)
|
2021-05-11 14:20:14 +02:00
|
|
|
# check event (agenda, slug) unicity
|
|
|
|
agenda2 = Agenda.objects.create(label='Foo Bar 2', kind='events')
|
2021-06-30 15:50:00 +02:00
|
|
|
Desk.objects.create(agenda=agenda2, slug='_exceptions_holder')
|
2021-05-11 14:20:14 +02:00
|
|
|
Event.objects.create(
|
|
|
|
slug='event',
|
|
|
|
agenda=agenda2,
|
|
|
|
places=42,
|
|
|
|
start_datetime=now(),
|
|
|
|
)
|
2019-10-02 13:30:37 +02:00
|
|
|
|
|
|
|
output = get_output_of_command('export_site')
|
2021-05-11 14:20:14 +02:00
|
|
|
assert len(json.loads(output)['agendas']) == 2
|
2019-10-02 13:30:37 +02:00
|
|
|
import_site(data={}, clean=True)
|
|
|
|
|
|
|
|
with tempfile.NamedTemporaryFile() as f:
|
|
|
|
f.write(force_bytes(output))
|
|
|
|
f.flush()
|
|
|
|
call_command('import_site', f.name)
|
|
|
|
|
2021-05-11 14:20:14 +02:00
|
|
|
assert Agenda.objects.count() == 2
|
|
|
|
assert Event.objects.count() == 2
|
2020-07-21 16:38:14 +02:00
|
|
|
first_imported_event = Agenda.objects.get(label='Foo Bar').event_set.first()
|
2021-05-11 14:20:14 +02:00
|
|
|
assert first_imported_event.slug == 'event'
|
2019-10-02 13:30:37 +02:00
|
|
|
assert first_imported_event.description == 'description'
|
2019-12-23 18:59:38 +01:00
|
|
|
assert first_imported_event.pricing == '100'
|
|
|
|
assert first_imported_event.url == 'https://example.net/'
|
2021-10-08 15:48:14 +02:00
|
|
|
assert str(first_imported_event.publication_datetime) == '2020-05-10 22:00:00+00:00'
|
|
|
|
assert str(first_imported_event.publication_datetime.tzinfo) == 'UTC'
|
2021-09-08 12:24:15 +02:00
|
|
|
assert first_imported_event.duration == 30
|
2021-05-11 14:20:14 +02:00
|
|
|
assert Agenda.objects.get(label='Foo Bar 2').event_set.first().slug == 'event'
|
2019-10-02 13:30:37 +02:00
|
|
|
|
|
|
|
|
2020-12-22 17:26:29 +01:00
|
|
|
def test_import_export_recurring_event(app, freezer):
|
|
|
|
freezer.move_to('2021-01-12 12:10')
|
|
|
|
agenda = Agenda.objects.create(label='Foo Bar', kind='events')
|
2021-07-09 15:41:40 +02:00
|
|
|
Desk.objects.create(agenda=agenda, slug='_exceptions_holder')
|
2020-12-22 17:26:29 +01:00
|
|
|
event = Event.objects.create(
|
|
|
|
agenda=agenda,
|
|
|
|
start_datetime=now(),
|
2023-06-28 12:46:16 +02:00
|
|
|
recurrence_days=[now().isoweekday()],
|
2021-04-21 16:21:31 +02:00
|
|
|
recurrence_week_interval=2,
|
2020-12-22 17:26:29 +01:00
|
|
|
places=10,
|
2021-01-19 15:35:31 +01:00
|
|
|
slug='test',
|
2020-12-22 17:26:29 +01:00
|
|
|
)
|
2022-03-16 15:10:34 +01:00
|
|
|
assert Event.objects.count() == 1
|
2020-12-22 17:26:29 +01:00
|
|
|
|
|
|
|
output = get_output_of_command('export_site')
|
|
|
|
assert len(json.loads(output)['agendas']) == 1
|
|
|
|
import_site(data={}, clean=True)
|
|
|
|
|
|
|
|
with tempfile.NamedTemporaryFile() as f:
|
|
|
|
f.write(force_bytes(output))
|
|
|
|
f.flush()
|
|
|
|
call_command('import_site', f.name)
|
|
|
|
|
|
|
|
assert Agenda.objects.count() == 1
|
2022-03-16 15:10:34 +01:00
|
|
|
assert Event.objects.count() == 28
|
|
|
|
event = Agenda.objects.get(label='Foo Bar').event_set.filter(primary_event__isnull=True).get()
|
2023-06-28 12:46:16 +02:00
|
|
|
assert event.recurrence_days == [now().isoweekday()]
|
2021-04-21 16:21:31 +02:00
|
|
|
assert event.recurrence_week_interval == 2
|
2020-12-22 17:26:29 +01:00
|
|
|
|
2022-03-16 15:10:34 +01:00
|
|
|
# importing event with end recurrence date removes recurrences
|
2021-01-19 15:35:31 +01:00
|
|
|
event.recurrence_end_date = now() + datetime.timedelta(days=7)
|
2021-04-21 16:21:31 +02:00
|
|
|
event.recurrence_week_interval = 1
|
2021-01-19 15:35:31 +01:00
|
|
|
event.save()
|
|
|
|
output = get_output_of_command('export_site')
|
|
|
|
import_site(data={}, clean=True)
|
|
|
|
|
|
|
|
with tempfile.NamedTemporaryFile() as f:
|
|
|
|
f.write(force_bytes(output))
|
|
|
|
f.flush()
|
|
|
|
call_command('import_site', f.name)
|
|
|
|
|
|
|
|
event = Event.objects.get(slug='test')
|
2022-03-16 15:10:34 +01:00
|
|
|
assert Event.objects.filter(primary_event=event).count() == 1
|
2021-01-19 15:35:31 +01:00
|
|
|
|
2021-03-05 11:41:02 +01:00
|
|
|
# import again
|
|
|
|
with tempfile.NamedTemporaryFile() as f:
|
|
|
|
f.write(force_bytes(output))
|
|
|
|
f.flush()
|
|
|
|
call_command('import_site', f.name)
|
|
|
|
|
|
|
|
event = Event.objects.get(slug='test')
|
2022-03-16 15:10:34 +01:00
|
|
|
assert Event.objects.filter(primary_event=event).count() == 1
|
2021-03-05 11:41:02 +01:00
|
|
|
|
|
|
|
# import again but change places
|
|
|
|
payload = json.loads(output)
|
|
|
|
payload['agendas'][0]['events'][0]['places'] = 42
|
|
|
|
with tempfile.NamedTemporaryFile() as f:
|
|
|
|
f.write(force_bytes(json.dumps(payload)))
|
|
|
|
f.flush()
|
|
|
|
call_command('import_site', f.name)
|
|
|
|
|
|
|
|
event = Event.objects.get(slug='test')
|
|
|
|
assert event.places == 42
|
2022-03-16 15:10:34 +01:00
|
|
|
assert Event.objects.filter(primary_event=event, places=42).count() == 1
|
2021-03-05 11:41:02 +01:00
|
|
|
|
2020-12-22 17:26:29 +01:00
|
|
|
|
2021-05-21 11:57:11 +02:00
|
|
|
def test_import_export_meetings_agenda_options(app):
|
|
|
|
agenda = Agenda.objects.create(
|
|
|
|
label='Foo Bar',
|
|
|
|
kind='meetings',
|
|
|
|
default_view='month',
|
|
|
|
)
|
|
|
|
|
|
|
|
output = get_output_of_command('export_site')
|
|
|
|
assert len(json.loads(output)['agendas']) == 1
|
|
|
|
import_site(data={}, clean=True)
|
|
|
|
|
|
|
|
with tempfile.NamedTemporaryFile() as f:
|
|
|
|
f.write(force_bytes(output))
|
|
|
|
f.flush()
|
|
|
|
call_command('import_site', f.name)
|
|
|
|
|
|
|
|
assert Agenda.objects.count() == 1
|
|
|
|
agenda = Agenda.objects.first()
|
|
|
|
assert agenda.default_view == 'month'
|
|
|
|
|
|
|
|
|
2020-07-21 16:38:14 +02:00
|
|
|
def test_import_export_permissions(app):
|
|
|
|
meetings_agenda = Agenda.objects.create(label='Foo Bar', kind='meetings')
|
|
|
|
group1 = Group.objects.create(name='gé1')
|
|
|
|
group2 = Group.objects.create(name='gé2')
|
2018-11-13 20:44:51 +01:00
|
|
|
meetings_agenda.view_role = group1
|
|
|
|
meetings_agenda.edit_role = group2
|
|
|
|
meetings_agenda.save()
|
|
|
|
output = get_output_of_command('export_site')
|
2020-07-21 16:38:14 +02:00
|
|
|
assert len(json.loads(output)['agendas']) == 1
|
2018-11-13 20:44:51 +01:00
|
|
|
import_site(data={}, clean=True)
|
|
|
|
assert Agenda.objects.count() == 0
|
|
|
|
Group.objects.all().delete()
|
|
|
|
|
|
|
|
with pytest.raises(AgendaImportError) as excinfo:
|
|
|
|
import_site(json.loads(output), overwrite=True)
|
2020-06-18 16:20:18 +02:00
|
|
|
assert 'gé1' in str(excinfo.value) and 'gé2' in str(excinfo.value)
|
2018-11-13 20:44:51 +01:00
|
|
|
|
|
|
|
group1 = Group(name='gé1')
|
|
|
|
group1.save()
|
|
|
|
with pytest.raises(AgendaImportError) as excinfo:
|
|
|
|
import_site(json.loads(output), overwrite=True)
|
2020-06-18 16:20:18 +02:00
|
|
|
assert '%s' % excinfo.value == 'Missing roles: "gé2"'
|
2018-11-13 20:44:51 +01:00
|
|
|
|
|
|
|
with tempfile.NamedTemporaryFile() as f:
|
|
|
|
f.write(force_bytes(output))
|
|
|
|
f.flush()
|
|
|
|
with pytest.raises(CommandError) as excinfo:
|
|
|
|
call_command('import_site', f.name)
|
2020-06-18 16:20:18 +02:00
|
|
|
assert '%s' % excinfo.value == 'Missing roles: "gé2"'
|
2018-11-13 20:44:51 +01:00
|
|
|
|
|
|
|
group2 = Group(name='gé2')
|
|
|
|
group2.save()
|
|
|
|
import_site(json.loads(output), overwrite=True)
|
|
|
|
|
|
|
|
agenda = Agenda.objects.get(slug=meetings_agenda.slug)
|
|
|
|
assert agenda.view_role == group1
|
|
|
|
assert agenda.edit_role == group2
|
2020-03-17 13:11:49 +01:00
|
|
|
|
|
|
|
|
2022-04-01 14:25:41 +02:00
|
|
|
def test_import_export_agenda_with_resources(app):
|
2020-07-21 16:38:14 +02:00
|
|
|
meetings_agenda = Agenda.objects.create(label='Foo Bar', kind='meetings')
|
2020-05-15 15:47:03 +02:00
|
|
|
resource = Resource.objects.create(label='foo')
|
|
|
|
meetings_agenda.resources.add(resource)
|
|
|
|
output = get_output_of_command('export_site')
|
|
|
|
|
|
|
|
import_site(data={}, clean=True)
|
|
|
|
assert Agenda.objects.count() == 0
|
2022-04-01 14:25:41 +02:00
|
|
|
assert Resource.objects.count() == 0
|
|
|
|
data = json.loads(output)
|
|
|
|
del data['resources']
|
2020-05-15 15:47:03 +02:00
|
|
|
|
|
|
|
with pytest.raises(AgendaImportError) as excinfo:
|
2022-04-01 14:25:41 +02:00
|
|
|
import_site(data, overwrite=True)
|
2020-05-15 15:47:03 +02:00
|
|
|
assert str(excinfo.value) == 'Missing "foo" resource'
|
|
|
|
|
2022-04-01 14:25:41 +02:00
|
|
|
Resource.objects.create(label='foobar')
|
2020-05-15 15:47:03 +02:00
|
|
|
with pytest.raises(AgendaImportError) as excinfo:
|
2022-04-01 14:25:41 +02:00
|
|
|
import_site(data, overwrite=True)
|
2020-05-15 15:47:03 +02:00
|
|
|
assert str(excinfo.value) == 'Missing "foo" resource'
|
|
|
|
|
|
|
|
resource = Resource.objects.create(label='foo')
|
2022-04-01 14:25:41 +02:00
|
|
|
import_site(data, overwrite=True)
|
2020-05-15 15:47:03 +02:00
|
|
|
agenda = Agenda.objects.get(slug=meetings_agenda.slug)
|
|
|
|
assert list(agenda.resources.all()) == [resource]
|
|
|
|
|
|
|
|
|
2022-04-01 14:25:41 +02:00
|
|
|
def test_import_export_agenda_with_category(app):
|
2020-07-24 15:59:49 +02:00
|
|
|
category = Category.objects.create(label='foo')
|
|
|
|
agenda = Agenda.objects.create(label='Foo Bar', category=category)
|
2021-06-30 15:50:00 +02:00
|
|
|
Desk.objects.create(agenda=agenda, slug='_exceptions_holder')
|
2020-07-24 15:59:49 +02:00
|
|
|
output = get_output_of_command('export_site')
|
|
|
|
|
|
|
|
import_site(data={}, clean=True)
|
|
|
|
assert Agenda.objects.count() == 0
|
2021-12-08 17:58:20 +01:00
|
|
|
assert Category.objects.count() == 0
|
|
|
|
data = json.loads(output)
|
|
|
|
del data['categories']
|
2020-07-24 15:59:49 +02:00
|
|
|
|
2021-12-08 18:44:59 +01:00
|
|
|
import_site(data.copy(), overwrite=True)
|
|
|
|
agenda = Agenda.objects.get(slug=agenda.slug)
|
|
|
|
assert agenda.category is None
|
2020-07-24 15:59:49 +02:00
|
|
|
|
|
|
|
category = Category.objects.create(label='foobar')
|
2021-12-08 18:44:59 +01:00
|
|
|
import_site(data.copy(), overwrite=True)
|
|
|
|
agenda = Agenda.objects.get(slug=agenda.slug)
|
|
|
|
assert agenda.category is None
|
2020-07-24 15:59:49 +02:00
|
|
|
|
|
|
|
category = Category.objects.create(label='foo')
|
2021-12-08 18:44:59 +01:00
|
|
|
import_site(data.copy(), overwrite=True)
|
2020-07-24 15:59:49 +02:00
|
|
|
agenda = Agenda.objects.get(slug=agenda.slug)
|
|
|
|
assert agenda.category == category
|
|
|
|
|
|
|
|
|
2022-04-04 15:55:55 +02:00
|
|
|
def test_import_export_agenda_with_events_type(app):
|
|
|
|
events_type = EventsType.objects.create(label='foo')
|
|
|
|
agenda = Agenda.objects.create(label='Foo Bar', kind='events', events_type=events_type)
|
|
|
|
Desk.objects.create(agenda=agenda, slug='_exceptions_holder')
|
|
|
|
output = get_output_of_command('export_site')
|
|
|
|
|
|
|
|
import_site(data={}, clean=True)
|
|
|
|
assert Agenda.objects.count() == 0
|
|
|
|
assert EventsType.objects.count() == 0
|
|
|
|
data = json.loads(output)
|
|
|
|
del data['events_types']
|
|
|
|
|
|
|
|
with pytest.raises(AgendaImportError) as excinfo:
|
|
|
|
import_site(data, overwrite=True)
|
|
|
|
assert str(excinfo.value) == 'Missing "foo" events type'
|
|
|
|
|
|
|
|
EventsType.objects.create(label='foobar')
|
|
|
|
with pytest.raises(AgendaImportError) as excinfo:
|
|
|
|
import_site(data, overwrite=True)
|
|
|
|
assert str(excinfo.value) == 'Missing "foo" events type'
|
|
|
|
|
|
|
|
events_type = EventsType.objects.create(label='foo')
|
|
|
|
import_site(data, overwrite=True)
|
|
|
|
agenda = Agenda.objects.get(slug=agenda.slug)
|
|
|
|
assert agenda.events_type == events_type
|
|
|
|
|
|
|
|
|
2020-03-17 13:11:49 +01:00
|
|
|
def test_import_export_virtual_agenda(app):
|
|
|
|
virtual_agenda = Agenda.objects.create(label='Virtual Agenda', kind='virtual')
|
|
|
|
output = get_output_of_command('export_site')
|
|
|
|
payload = json.loads(output)
|
|
|
|
assert len(payload['agendas']) == 1
|
|
|
|
virtual_agenda.delete()
|
|
|
|
import_site(json.loads(output), overwrite=True)
|
|
|
|
|
|
|
|
virtual_agenda = Agenda.objects.get(label='Virtual Agenda', slug='virtual-agenda', kind='virtual')
|
|
|
|
assert virtual_agenda.minimal_booking_delay is None
|
|
|
|
assert virtual_agenda.maximal_booking_delay is None
|
|
|
|
assert virtual_agenda.real_agendas.count() == 0
|
|
|
|
assert virtual_agenda.excluded_timeperiods.count() == 0
|
|
|
|
|
|
|
|
# add booking delay
|
|
|
|
virtual_agenda.minimal_booking_delay = 2
|
|
|
|
virtual_agenda.maximal_booking_delay = 10
|
|
|
|
virtual_agenda.save()
|
|
|
|
output = get_output_of_command('export_site')
|
|
|
|
payload = json.loads(output)
|
|
|
|
virtual_agenda.delete()
|
|
|
|
import_site(json.loads(output), overwrite=True)
|
|
|
|
virtual_agenda = Agenda.objects.get(label='Virtual Agenda', slug='virtual-agenda', kind='virtual')
|
|
|
|
assert virtual_agenda.minimal_booking_delay == 2
|
|
|
|
assert virtual_agenda.maximal_booking_delay == 10
|
|
|
|
|
|
|
|
# add excluded timeperiods
|
|
|
|
tp1 = TimePeriod.objects.create(
|
|
|
|
agenda=virtual_agenda, weekday=1, start_time=datetime.time(10, 0), end_time=datetime.time(11, 0)
|
|
|
|
)
|
|
|
|
tp2 = TimePeriod.objects.create(
|
|
|
|
agenda=virtual_agenda, weekday=2, start_time=datetime.time(12, 0), end_time=datetime.time(13, 0)
|
|
|
|
)
|
|
|
|
output = get_output_of_command('export_site')
|
|
|
|
payload = json.loads(output)
|
|
|
|
virtual_agenda.delete()
|
|
|
|
tp1.delete()
|
|
|
|
tp2.delete()
|
|
|
|
import_site(json.loads(output), overwrite=True)
|
|
|
|
virtual_agenda = Agenda.objects.get(label='Virtual Agenda', slug='virtual-agenda', kind='virtual')
|
|
|
|
assert virtual_agenda.excluded_timeperiods.count() == 2
|
|
|
|
tp1 = TimePeriod.objects.get(
|
|
|
|
agenda=virtual_agenda, weekday=1, start_time=datetime.time(10, 0), end_time=datetime.time(11, 0)
|
|
|
|
)
|
|
|
|
tp2 = TimePeriod.objects.get(
|
|
|
|
agenda=virtual_agenda, weekday=2, start_time=datetime.time(12, 0), end_time=datetime.time(13, 0)
|
|
|
|
)
|
|
|
|
|
|
|
|
|
|
|
|
def test_import_export_virtual_agenda_with_included_agenda(app):
|
|
|
|
virtual_agenda = Agenda.objects.create(label='Virtual Agenda', kind='virtual')
|
2023-06-22 14:39:02 +02:00
|
|
|
foo_agenda = Agenda.objects.create(label='Zoo', kind='meetings')
|
2020-03-17 13:11:49 +01:00
|
|
|
bar_agenda = Agenda.objects.create(label='Bar', kind='meetings')
|
|
|
|
mt1 = MeetingType.objects.create(agenda=foo_agenda, label='Meeting Type', duration=30)
|
|
|
|
mt2 = MeetingType.objects.create(agenda=bar_agenda, label='Meeting Type', duration=30)
|
|
|
|
VirtualMember.objects.create(virtual_agenda=virtual_agenda, real_agenda=foo_agenda)
|
|
|
|
VirtualMember.objects.create(virtual_agenda=virtual_agenda, real_agenda=bar_agenda)
|
|
|
|
output = get_output_of_command('export_site')
|
|
|
|
payload = json.loads(output)
|
|
|
|
assert len(payload['agendas']) == 3
|
|
|
|
virtual_agenda.delete()
|
|
|
|
foo_agenda.delete()
|
|
|
|
bar_agenda.delete()
|
|
|
|
mt1.delete()
|
|
|
|
mt2.delete()
|
|
|
|
import_site(payload, overwrite=True)
|
|
|
|
|
|
|
|
virtual_agenda = Agenda.objects.get(label='Virtual Agenda', slug='virtual-agenda', kind='virtual')
|
|
|
|
assert virtual_agenda.real_agendas.count() == 2
|
2023-06-22 14:39:02 +02:00
|
|
|
assert virtual_agenda.real_agendas.filter(label='Zoo').count() == 1
|
2020-03-17 13:11:49 +01:00
|
|
|
assert virtual_agenda.real_agendas.filter(label='Bar').count() == 1
|
|
|
|
|
|
|
|
# add incompatible meetingtype
|
|
|
|
bar_agenda = Agenda.objects.get(label='Bar', kind='meetings')
|
|
|
|
mt2 = MeetingType.objects.get(agenda=bar_agenda, label='Meeting Type')
|
|
|
|
mt2.duration = 10
|
|
|
|
mt2.save()
|
|
|
|
output = get_output_of_command('export_site')
|
|
|
|
payload = json.loads(output)
|
|
|
|
virtual_agenda.delete()
|
|
|
|
with pytest.raises(AgendaImportError) as excinfo:
|
|
|
|
import_site(json.loads(output), overwrite=False)
|
|
|
|
assert (
|
|
|
|
'This agenda does not have the same meeting types provided by the virtual agenda.'
|
|
|
|
in '%s' % excinfo.value
|
|
|
|
)
|
2020-04-28 16:49:04 +02:00
|
|
|
|
|
|
|
|
2020-07-21 14:48:42 +02:00
|
|
|
def test_import_export_virtual_agenda_with_missing_agenda(app):
|
|
|
|
virtual_agenda = Agenda.objects.create(label='Virtual Agenda', kind='virtual')
|
|
|
|
foo_agenda = Agenda.objects.create(label='Foo', kind='meetings')
|
|
|
|
VirtualMember.objects.create(virtual_agenda=virtual_agenda, real_agenda=foo_agenda)
|
|
|
|
output = get_output_of_command('export_site')
|
|
|
|
payload = json.loads(output)
|
|
|
|
del payload['agendas'][0] # remove real agenda
|
|
|
|
|
|
|
|
virtual_agenda.delete()
|
|
|
|
foo_agenda.delete()
|
|
|
|
with pytest.raises(AgendaImportError) as excinfo:
|
|
|
|
import_site(payload, overwrite=False)
|
|
|
|
assert 'The real agenda "foo" does not exist.' in '%s' % excinfo.value
|
|
|
|
|
|
|
|
|
2020-07-21 16:38:14 +02:00
|
|
|
def test_import_export_desk_missing_fields(app):
|
|
|
|
meetings_agenda = Agenda.objects.create(label='Foo Bar', kind='meetings')
|
|
|
|
MeetingType.objects.create(agenda=meetings_agenda, label='Meeting Type', duration=30)
|
|
|
|
desk = Desk.objects.create(agenda=meetings_agenda, label='Desk')
|
|
|
|
TimePeriod.objects.create(
|
|
|
|
desk=desk, weekday=2, start_time=datetime.time(10, 0), end_time=datetime.time(11, 0)
|
|
|
|
)
|
|
|
|
TimePeriodException.objects.create(
|
|
|
|
desk=desk,
|
|
|
|
start_datetime=make_aware(datetime.datetime(2017, 5, 22, 8, 0)),
|
|
|
|
end_datetime=make_aware(datetime.datetime(2017, 5, 22, 12, 30)),
|
|
|
|
)
|
2020-04-28 16:49:04 +02:00
|
|
|
output = get_output_of_command('export_site')
|
|
|
|
payload = json.loads(output)
|
|
|
|
del payload['agendas'][0]['desks'][0]['timeperiods']
|
|
|
|
del payload['agendas'][0]['desks'][0]['exceptions']
|
|
|
|
Agenda.objects.all().delete()
|
|
|
|
import_site(payload)
|
|
|
|
assert TimePeriod.objects.exists() is False
|
|
|
|
assert TimePeriodException.objects.exists() is False
|
2020-05-07 11:25:44 +02:00
|
|
|
|
|
|
|
|
2020-11-17 14:43:29 +01:00
|
|
|
def test_import_export_unknown_fields(app):
|
2020-07-21 16:38:14 +02:00
|
|
|
events_agenda = Agenda.objects.create(label='Events Agenda', kind='events')
|
2021-06-30 15:50:00 +02:00
|
|
|
Desk.objects.create(agenda=events_agenda, slug='_exceptions_holder')
|
2020-07-21 16:38:14 +02:00
|
|
|
Event.objects.create(agenda=events_agenda, start_datetime=now(), places=10)
|
|
|
|
meetings_agenda = Agenda.objects.create(label='Meetings Agenda', kind='meetings')
|
|
|
|
MeetingType.objects.create(agenda=meetings_agenda, label='Meeting Type', duration=30)
|
|
|
|
Desk.objects.create(agenda=meetings_agenda, label='Desk')
|
2020-05-07 11:25:44 +02:00
|
|
|
desk = meetings_agenda.desk_set.first()
|
2020-07-21 16:38:14 +02:00
|
|
|
TimePeriod.objects.create(
|
|
|
|
desk=desk, weekday=2, start_time=datetime.time(10, 0), end_time=datetime.time(11, 0)
|
|
|
|
)
|
|
|
|
TimePeriodException.objects.create(
|
|
|
|
desk=desk,
|
|
|
|
start_datetime=make_aware(datetime.datetime(2017, 5, 22, 8, 0)),
|
|
|
|
end_datetime=make_aware(datetime.datetime(2017, 5, 22, 12, 30)),
|
2020-05-07 11:25:44 +02:00
|
|
|
)
|
|
|
|
|
|
|
|
output = get_output_of_command('export_site')
|
|
|
|
payload = json.loads(output)
|
|
|
|
|
|
|
|
Agenda.objects.all().delete()
|
|
|
|
assert Agenda.objects.exists() is False
|
|
|
|
assert MeetingType.objects.exists() is False
|
|
|
|
assert Desk.objects.exists() is False
|
|
|
|
assert TimePeriod.objects.exists() is False
|
|
|
|
assert TimePeriodException.objects.exists() is False
|
|
|
|
|
|
|
|
# add unknown fields everywhere
|
2020-07-21 16:38:14 +02:00
|
|
|
payload['agendas'][0]['unknown_field'] = 'foobar'
|
|
|
|
payload['agendas'][0]['events'][0]['unknown_field'] = 'foobar'
|
2020-11-17 14:43:29 +01:00
|
|
|
payload['agendas'][0]['real_agendas'] = ['foobar'] # not available for a non virtual agenda
|
2020-07-21 16:38:14 +02:00
|
|
|
payload['agendas'][1]['unknown_field'] = 'foobar'
|
|
|
|
payload['agendas'][1]['meetingtypes'][0]['unknown_field'] = 'foobar'
|
|
|
|
payload['agendas'][1]['desks'][0]['unknown_field'] = 'foobar'
|
|
|
|
payload['agendas'][1]['desks'][0]['timeperiods'][0]['unknown_field'] = 'foobar'
|
|
|
|
payload['agendas'][1]['desks'][0]['exceptions'][0]['unknown_field'] = 'foobar'
|
2020-05-07 11:25:44 +02:00
|
|
|
|
|
|
|
import_site(payload)
|
|
|
|
assert Agenda.objects.exists() is True
|
|
|
|
assert MeetingType.objects.exists() is True
|
|
|
|
assert Desk.objects.exists() is True
|
|
|
|
assert TimePeriod.objects.exists() is True
|
|
|
|
assert TimePeriodException.objects.exists() is True
|
2020-07-21 16:13:57 +02:00
|
|
|
|
|
|
|
|
|
|
|
def test_import_export_slug_fields(app):
|
|
|
|
agenda_events = Agenda.objects.create(label='Events Agenda', kind='events')
|
2021-06-30 15:50:00 +02:00
|
|
|
Desk.objects.create(agenda=agenda_events, slug='_exceptions_holder')
|
2020-07-21 16:38:14 +02:00
|
|
|
Event.objects.create(agenda=agenda_events, start_datetime=now(), places=10)
|
2020-07-21 16:13:57 +02:00
|
|
|
agenda_meetings = Agenda.objects.create(label='Meetings Agenda', kind='meetings')
|
|
|
|
MeetingType.objects.create(agenda=agenda_meetings, label='Meeting Type', duration=30)
|
|
|
|
Desk.objects.create(agenda=agenda_meetings, label='Desk')
|
|
|
|
|
|
|
|
output = get_output_of_command('export_site')
|
|
|
|
original_payload = json.loads(output)
|
|
|
|
|
|
|
|
Agenda.objects.all().delete()
|
|
|
|
assert Agenda.objects.exists() is False
|
|
|
|
assert MeetingType.objects.exists() is False
|
|
|
|
assert Desk.objects.exists() is False
|
|
|
|
assert Event.objects.exists() is False
|
|
|
|
|
|
|
|
payload = copy.deepcopy(original_payload)
|
|
|
|
payload['agendas'][0]['slug'] = 'events-agenda&'
|
|
|
|
with pytest.raises(AgendaImportError) as excinfo:
|
|
|
|
import_site(payload)
|
|
|
|
assert str(excinfo.value) == 'Bad slug format "events-agenda&"'
|
|
|
|
|
|
|
|
payload = copy.deepcopy(original_payload)
|
|
|
|
payload['agendas'][0]['events'][0]['slug'] = 'events-agenda-event&'
|
|
|
|
with pytest.raises(AgendaImportError) as excinfo:
|
|
|
|
import_site(payload)
|
|
|
|
assert str(excinfo.value) == 'Bad slug format "events-agenda-event&"'
|
|
|
|
|
|
|
|
payload = copy.deepcopy(original_payload)
|
|
|
|
payload['agendas'][1]['desks'][0]['slug'] = 'desk&'
|
|
|
|
with pytest.raises(AgendaImportError) as excinfo:
|
|
|
|
import_site(payload)
|
|
|
|
assert str(excinfo.value) == 'Bad slug format "desk&"'
|
|
|
|
|
|
|
|
payload = copy.deepcopy(original_payload)
|
|
|
|
payload['agendas'][1]['meetingtypes'][0]['slug'] = 'meeting-type&'
|
|
|
|
with pytest.raises(AgendaImportError) as excinfo:
|
|
|
|
import_site(payload)
|
|
|
|
assert str(excinfo.value) == 'Bad slug format "meeting-type&"'
|
2020-07-16 15:12:47 +02:00
|
|
|
|
|
|
|
|
|
|
|
def test_import_export_notification_settings():
|
|
|
|
agenda = Agenda.objects.create(label='Foo bar', kind='events')
|
2021-06-30 15:50:00 +02:00
|
|
|
Desk.objects.create(agenda=agenda, slug='_exceptions_holder')
|
2020-10-02 11:18:11 +02:00
|
|
|
AgendaNotificationsSettings.objects.create(
|
2020-07-16 15:12:47 +02:00
|
|
|
agenda=agenda,
|
|
|
|
almost_full_event=AgendaNotificationsSettings.EDIT_ROLE,
|
|
|
|
full_event=AgendaNotificationsSettings.VIEW_ROLE,
|
|
|
|
cancelled_event=AgendaNotificationsSettings.EMAIL_FIELD,
|
|
|
|
cancelled_event_emails=['hop@entrouvert.com', 'top@entrouvert.com'],
|
|
|
|
)
|
|
|
|
output = get_output_of_command('export_site')
|
|
|
|
payload = json.loads(output)
|
|
|
|
|
|
|
|
agenda.delete()
|
|
|
|
assert not AgendaNotificationsSettings.objects.exists()
|
|
|
|
|
|
|
|
import_site(payload)
|
|
|
|
agenda = Agenda.objects.first()
|
|
|
|
AgendaNotificationsSettings.objects.get(
|
|
|
|
agenda=agenda,
|
|
|
|
almost_full_event=AgendaNotificationsSettings.EDIT_ROLE,
|
|
|
|
full_event=AgendaNotificationsSettings.VIEW_ROLE,
|
|
|
|
cancelled_event=AgendaNotificationsSettings.EMAIL_FIELD,
|
|
|
|
cancelled_event_emails=['hop@entrouvert.com', 'top@entrouvert.com'],
|
|
|
|
)
|
2020-09-15 14:05:38 +02:00
|
|
|
|
2020-10-02 11:18:11 +02:00
|
|
|
# again - check OneToOneField
|
|
|
|
import_site(payload)
|
|
|
|
|
2020-09-15 14:05:38 +02:00
|
|
|
|
|
|
|
def test_import_export_reminder_settings():
|
|
|
|
agenda = Agenda.objects.create(label='Foo bar', kind='events')
|
2021-06-30 15:50:00 +02:00
|
|
|
Desk.objects.create(agenda=agenda, slug='_exceptions_holder')
|
2020-10-02 11:18:11 +02:00
|
|
|
AgendaReminderSettings.objects.create(
|
2020-09-15 14:05:38 +02:00
|
|
|
agenda=agenda,
|
2022-02-02 17:45:15 +01:00
|
|
|
days_before_email=2,
|
|
|
|
days_before_sms=1,
|
2020-09-15 14:05:38 +02:00
|
|
|
email_extra_info='test',
|
|
|
|
)
|
|
|
|
output = get_output_of_command('export_site')
|
|
|
|
payload = json.loads(output)
|
|
|
|
|
|
|
|
agenda.delete()
|
|
|
|
assert not AgendaReminderSettings.objects.exists()
|
|
|
|
|
|
|
|
import_site(payload)
|
|
|
|
agenda = Agenda.objects.first()
|
|
|
|
AgendaReminderSettings.objects.get(
|
|
|
|
agenda=agenda,
|
2022-02-02 17:45:15 +01:00
|
|
|
days_before_email=2,
|
|
|
|
days_before_sms=1,
|
2020-09-15 14:05:38 +02:00
|
|
|
email_extra_info='test',
|
|
|
|
)
|
2020-10-02 11:18:11 +02:00
|
|
|
|
|
|
|
# again - check OneToOneField
|
|
|
|
import_site(payload)
|
2020-10-26 18:09:53 +01:00
|
|
|
|
|
|
|
|
|
|
|
@override_settings(
|
|
|
|
EXCEPTIONS_SOURCES={
|
|
|
|
'holidays': {'class': 'workalendar.europe.France', 'label': 'Holidays'},
|
|
|
|
}
|
|
|
|
)
|
|
|
|
def test_import_export_time_period_exception_source():
|
|
|
|
agenda = Agenda.objects.create(label='Foo bar', kind='meetings')
|
|
|
|
desk = Desk.objects.create(slug='test', agenda=agenda)
|
|
|
|
desk.import_timeperiod_exceptions_from_settings(enable=True)
|
|
|
|
|
|
|
|
output = get_output_of_command('export_site')
|
|
|
|
payload = json.loads(output)
|
|
|
|
|
|
|
|
agenda.delete()
|
|
|
|
assert not TimePeriodExceptionSource.objects.exists()
|
|
|
|
|
|
|
|
import_site(payload)
|
|
|
|
desk = Desk.objects.get(slug='test')
|
|
|
|
source = desk.timeperiodexceptionsource_set.first()
|
|
|
|
assert source.enabled
|
|
|
|
assert desk.timeperiodexception_set.exists()
|
|
|
|
|
|
|
|
source.disable()
|
|
|
|
output = get_output_of_command('export_site')
|
|
|
|
payload = json.loads(output)
|
|
|
|
Agenda.objects.all().delete()
|
|
|
|
|
|
|
|
import_site(payload)
|
|
|
|
desk = Desk.objects.get(slug='test')
|
|
|
|
source = desk.timeperiodexceptionsource_set.first()
|
|
|
|
assert not source.enabled
|
|
|
|
assert not desk.timeperiodexception_set.exists()
|
2020-10-30 15:00:49 +01:00
|
|
|
|
|
|
|
|
2021-06-30 15:50:00 +02:00
|
|
|
@override_settings(
|
|
|
|
EXCEPTIONS_SOURCES={
|
|
|
|
'holidays': {'class': 'workalendar.europe.France', 'label': 'Holidays'},
|
|
|
|
}
|
|
|
|
)
|
|
|
|
def test_import_export_time_period_exception_source_enabled():
|
|
|
|
agenda = Agenda.objects.create(label='Foo bar', kind='events')
|
|
|
|
desk = Desk.objects.create(agenda=agenda, slug='_exceptions_holder')
|
|
|
|
desk.import_timeperiod_exceptions_from_settings()
|
|
|
|
source = desk.timeperiodexceptionsource_set.first()
|
|
|
|
assert not source.enabled
|
|
|
|
assert source.settings_slug == 'holidays'
|
|
|
|
source.enabled = True
|
|
|
|
source.save()
|
|
|
|
|
|
|
|
output = get_output_of_command('export_site')
|
|
|
|
payload = json.loads(output)
|
|
|
|
agenda.delete()
|
|
|
|
assert not TimePeriodExceptionSource.objects.exists()
|
|
|
|
|
|
|
|
import_site(payload)
|
|
|
|
agenda = Agenda.objects.get(label='Foo bar')
|
|
|
|
assert agenda.desk_set.count() == 1
|
|
|
|
desk = agenda.desk_set.first()
|
|
|
|
assert desk.timeperiodexceptionsource_set.count() == 1
|
|
|
|
source = desk.timeperiodexceptionsource_set.first()
|
|
|
|
assert source.enabled
|
|
|
|
assert source.settings_slug == 'holidays'
|
|
|
|
|
|
|
|
|
2023-08-17 13:42:03 +02:00
|
|
|
@mock.patch('chrono.agendas.models.requests.get')
|
|
|
|
def test_import_export_time_period_exception_source_remote_ics(mocked_get):
|
|
|
|
agenda = Agenda.objects.create(label='Foo bar', kind='meetings')
|
|
|
|
desk = Desk.objects.create(label='Desk', agenda=agenda)
|
|
|
|
source = TimePeriodExceptionSource.objects.create(desk=desk, ics_url='http://example.com/sample.ics')
|
|
|
|
|
|
|
|
mocked_response = mock.Mock()
|
|
|
|
mocked_response.text = ICS_SAMPLE
|
|
|
|
mocked_get.return_value = mocked_response
|
|
|
|
|
|
|
|
source.refresh_timeperiod_exceptions_from_ics()
|
|
|
|
assert TimePeriodException.objects.count() == 2
|
|
|
|
|
|
|
|
output = get_output_of_command('export_site')
|
|
|
|
payload = json.loads(output)
|
|
|
|
|
|
|
|
Agenda.objects.all().delete()
|
|
|
|
assert not TimePeriodExceptionSource.objects.exists()
|
|
|
|
assert not TimePeriodException.objects.exists()
|
|
|
|
|
|
|
|
import_site(payload)
|
|
|
|
source = TimePeriodExceptionSource.objects.get()
|
|
|
|
assert source.timeperiodexception_set.count() == 2
|
|
|
|
assert TimePeriodException.objects.count() == 2
|
|
|
|
|
|
|
|
# import again changes nothing
|
|
|
|
import_site(payload)
|
|
|
|
assert TimePeriodExceptionSource.objects.count() == 1
|
|
|
|
assert TimePeriodException.objects.count() == 2
|
|
|
|
|
|
|
|
# empty remote ics
|
|
|
|
mocked_response.text = ICS_SAMPLE_WITH_NO_EVENTS
|
|
|
|
|
|
|
|
Agenda.objects.all().delete()
|
|
|
|
import_site(payload)
|
|
|
|
|
|
|
|
assert TimePeriodExceptionSource.objects.count() == 1
|
|
|
|
assert TimePeriodException.objects.count() == 0
|
|
|
|
|
|
|
|
|
|
|
|
@mock.patch('chrono.agendas.models.requests.get')
|
|
|
|
def test_import_export_time_period_exception_source_ics_file(mocked_get):
|
|
|
|
agenda = Agenda.objects.create(label='Foo bar', kind='meetings')
|
|
|
|
desk = Desk.objects.create(label='Desk', agenda=agenda)
|
|
|
|
source = TimePeriodExceptionSource.objects.create(
|
|
|
|
desk=desk, ics_filename='sample.ics', ics_file=ContentFile(ICS_SAMPLE, name='sample.ics')
|
|
|
|
)
|
|
|
|
|
|
|
|
source.refresh_timeperiod_exceptions_from_ics()
|
|
|
|
assert TimePeriodException.objects.count() == 2
|
|
|
|
|
|
|
|
output = get_output_of_command('export_site')
|
|
|
|
payload = json.loads(output)
|
|
|
|
|
|
|
|
Agenda.objects.all().delete()
|
|
|
|
assert not TimePeriodExceptionSource.objects.exists()
|
|
|
|
assert not TimePeriodException.objects.exists()
|
|
|
|
|
|
|
|
import_site(payload)
|
|
|
|
source = TimePeriodExceptionSource.objects.get()
|
|
|
|
assert source.timeperiodexception_set.count() == 2
|
|
|
|
assert TimePeriodException.objects.count() == 2
|
|
|
|
|
|
|
|
# import again changes nothing
|
|
|
|
import_site(payload)
|
|
|
|
assert TimePeriodExceptionSource.objects.count() == 1
|
|
|
|
assert TimePeriodException.objects.count() == 2
|
|
|
|
|
2024-03-15 14:02:57 +01:00
|
|
|
payload['agendas'][0]['desks'][0]['exception_sources'][0]['ics_file'] = 'garbage'
|
|
|
|
with pytest.raises(AgendaImportError) as excinfo:
|
|
|
|
import_site(payload)
|
|
|
|
assert '%s' % excinfo.value == 'Bad ics file'
|
|
|
|
|
2023-08-17 13:42:03 +02:00
|
|
|
|
|
|
|
@override_settings(
|
|
|
|
EXCEPTIONS_SOURCES={
|
|
|
|
'holidays': {'class': 'workalendar.europe.France', 'label': 'Holidays'},
|
|
|
|
}
|
|
|
|
)
|
|
|
|
def test_import_export_time_period_exception_legacy_file():
|
|
|
|
agenda = Agenda.objects.create(label='Foo bar', kind='events')
|
|
|
|
desk = Desk.objects.create(agenda=agenda, slug='_exceptions_holder')
|
|
|
|
desk.import_timeperiod_exceptions_from_settings()
|
|
|
|
|
|
|
|
output = get_output_of_command('export_site')
|
|
|
|
payload = json.loads(output)
|
|
|
|
source = payload['agendas'][0]['exceptions_desk']['exception_sources'][0]
|
|
|
|
del source['ics_file']
|
|
|
|
del source['ics_filename']
|
|
|
|
del source['ics_url']
|
|
|
|
|
|
|
|
agenda.delete()
|
|
|
|
assert not TimePeriodExceptionSource.objects.exists()
|
|
|
|
|
|
|
|
import_site(payload)
|
|
|
|
assert TimePeriodExceptionSource.objects.count() == 1
|
|
|
|
|
|
|
|
|
2020-10-30 15:00:49 +01:00
|
|
|
def test_import_export_do_not_duplicate_timeperiod_and_exceptions():
|
|
|
|
agenda = Agenda.objects.create(label='Foo bar', kind='meetings')
|
|
|
|
desk = Desk.objects.create(slug='test', agenda=agenda)
|
|
|
|
TimePeriod.objects.create(
|
|
|
|
desk=desk, weekday=2, start_time=datetime.time(10, 0), end_time=datetime.time(11, 0)
|
|
|
|
)
|
|
|
|
TimePeriod.objects.create(
|
|
|
|
desk=desk, weekday=3, start_time=datetime.time(10, 0), end_time=datetime.time(11, 0)
|
|
|
|
)
|
2020-11-24 11:46:03 +01:00
|
|
|
tpe1 = TimePeriodException.objects.create(
|
2020-10-30 15:00:49 +01:00
|
|
|
desk=desk,
|
|
|
|
start_datetime=make_aware(datetime.datetime(2017, 5, 22, 8, 0)),
|
|
|
|
end_datetime=make_aware(datetime.datetime(2017, 5, 22, 12, 30)),
|
|
|
|
)
|
|
|
|
TimePeriodException.objects.create(
|
|
|
|
desk=desk,
|
|
|
|
start_datetime=make_aware(datetime.datetime(2017, 6, 22, 8, 0)),
|
|
|
|
end_datetime=make_aware(datetime.datetime(2017, 6, 22, 12, 30)),
|
|
|
|
)
|
|
|
|
assert TimePeriod.objects.count() == 2
|
|
|
|
assert TimePeriodException.objects.count() == 2
|
|
|
|
output = get_output_of_command('export_site')
|
|
|
|
payload = json.loads(output)
|
|
|
|
import_site(payload)
|
|
|
|
|
|
|
|
assert TimePeriod.objects.count() == 2
|
|
|
|
assert TimePeriodException.objects.count() == 2
|
2020-10-26 17:15:47 +01:00
|
|
|
|
2020-11-24 11:46:03 +01:00
|
|
|
# duplicated exception
|
|
|
|
output = get_output_of_command('export_site')
|
|
|
|
payload = json.loads(output)
|
|
|
|
assert len(payload['agendas'][0]['desks'][0]['exceptions']) == 2
|
|
|
|
tpe2 = TimePeriodException.objects.create(
|
|
|
|
desk=desk,
|
|
|
|
start_datetime=make_aware(datetime.datetime(2017, 5, 22, 8, 0)),
|
|
|
|
end_datetime=make_aware(datetime.datetime(2017, 5, 22, 12, 30)),
|
|
|
|
)
|
|
|
|
assert TimePeriod.objects.count() == 2
|
|
|
|
assert TimePeriodException.objects.count() == 3
|
|
|
|
assert tpe1.update_datetime < tpe2.update_datetime
|
|
|
|
|
|
|
|
import_site(payload)
|
|
|
|
assert TimePeriod.objects.count() == 2
|
|
|
|
assert TimePeriodException.objects.count() == 3
|
|
|
|
tpe1.refresh_from_db()
|
|
|
|
tpe2.refresh_from_db()
|
|
|
|
assert tpe1.update_datetime == tpe2.update_datetime
|
|
|
|
|
2020-10-26 17:15:47 +01:00
|
|
|
|
|
|
|
def test_import_export_unavailability_calendar(app):
|
|
|
|
output = get_output_of_command('export_site')
|
|
|
|
payload = json.loads(output)
|
|
|
|
assert len(payload['unavailability_calendars']) == 0
|
|
|
|
|
|
|
|
group1 = Group.objects.create(name='gé1')
|
|
|
|
group2 = Group.objects.create(name='gé2')
|
|
|
|
calendar = UnavailabilityCalendar.objects.create(label='Calendar', view_role=group1, edit_role=group2)
|
|
|
|
tp1_start = make_aware(datetime.datetime(2017, 5, 22, 8, 0))
|
|
|
|
tp1_end = make_aware(datetime.datetime(2017, 5, 22, 12, 30))
|
|
|
|
tp1 = TimePeriodException.objects.create(
|
|
|
|
unavailability_calendar=calendar, start_datetime=tp1_start, end_datetime=tp1_end
|
|
|
|
)
|
|
|
|
tp2_start = make_aware(datetime.datetime(2018, 5, 22, 8, 0))
|
|
|
|
tp2_end = make_aware(datetime.datetime(2018, 5, 22, 12, 30))
|
|
|
|
tp2 = TimePeriodException.objects.create(
|
|
|
|
unavailability_calendar=calendar, start_datetime=tp2_start, end_datetime=tp2_end
|
|
|
|
)
|
|
|
|
meetings_agenda = Agenda.objects.create(label='Foo Bar', kind='meetings')
|
|
|
|
MeetingType.objects.create(agenda=meetings_agenda, label='Meeting Type', duration=30)
|
|
|
|
desk = Desk.objects.create(agenda=meetings_agenda, label='Desk')
|
|
|
|
desk.unavailability_calendars.add(calendar)
|
|
|
|
|
|
|
|
output = get_output_of_command('export_site')
|
|
|
|
payload = json.loads(output)
|
|
|
|
assert len(payload['unavailability_calendars']) == 1
|
|
|
|
assert len(payload['agendas']) == 1
|
|
|
|
|
|
|
|
calendar.delete()
|
|
|
|
tp1.delete()
|
|
|
|
tp2.delete()
|
|
|
|
meetings_agenda.delete()
|
|
|
|
assert not UnavailabilityCalendar.objects.exists()
|
|
|
|
assert not TimePeriodException.objects.exists()
|
|
|
|
assert not Agenda.objects.exists()
|
|
|
|
assert not Desk.objects.exists()
|
|
|
|
|
|
|
|
import_site(copy.deepcopy(payload))
|
|
|
|
assert UnavailabilityCalendar.objects.count() == 1
|
|
|
|
calendar = UnavailabilityCalendar.objects.first()
|
|
|
|
assert calendar.label == 'Calendar'
|
|
|
|
assert calendar.view_role == group1
|
|
|
|
assert calendar.edit_role == group2
|
|
|
|
assert calendar.timeperiodexception_set.count() == 2
|
|
|
|
assert TimePeriodException.objects.get(
|
|
|
|
unavailability_calendar=calendar, start_datetime=tp1_start, end_datetime=tp1_end
|
|
|
|
)
|
|
|
|
assert TimePeriodException.objects.get(
|
|
|
|
unavailability_calendar=calendar, start_datetime=tp2_start, end_datetime=tp2_end
|
|
|
|
)
|
|
|
|
|
|
|
|
agenda = Agenda.objects.get(label='Foo Bar')
|
|
|
|
desk = agenda.desk_set.first()
|
|
|
|
assert desk.unavailability_calendars.count() == 1
|
|
|
|
assert desk.unavailability_calendars.first() == calendar
|
|
|
|
|
|
|
|
# update
|
|
|
|
update_payload = copy.deepcopy(payload)
|
|
|
|
update_payload['unavailability_calendars'][0]['label'] = 'Calendar Updated'
|
|
|
|
import_site(update_payload)
|
|
|
|
calendar.refresh_from_db()
|
|
|
|
assert calendar.label == 'Calendar Updated'
|
2021-01-26 10:42:50 +01:00
|
|
|
|
|
|
|
|
2021-12-08 17:58:20 +01:00
|
|
|
def test_import_export_category(app):
|
|
|
|
output = get_output_of_command('export_site')
|
|
|
|
payload = json.loads(output)
|
|
|
|
assert len(payload['categories']) == 0
|
|
|
|
|
|
|
|
category = Category.objects.create(label='Foo bar')
|
|
|
|
|
|
|
|
output = get_output_of_command('export_site')
|
|
|
|
payload = json.loads(output)
|
|
|
|
assert len(payload['categories']) == 1
|
|
|
|
|
|
|
|
category.delete()
|
|
|
|
assert not Category.objects.exists()
|
|
|
|
|
|
|
|
import_site(copy.deepcopy(payload))
|
|
|
|
assert Category.objects.count() == 1
|
|
|
|
category = Category.objects.first()
|
|
|
|
assert category.label == 'Foo bar'
|
|
|
|
assert category.slug == 'foo-bar'
|
|
|
|
|
|
|
|
# update
|
|
|
|
update_payload = copy.deepcopy(payload)
|
|
|
|
update_payload['categories'][0]['label'] = 'Foo bar Updated'
|
|
|
|
import_site(update_payload)
|
|
|
|
category.refresh_from_db()
|
|
|
|
assert category.label == 'Foo bar Updated'
|
|
|
|
|
|
|
|
# insert another category
|
|
|
|
category.slug = 'foo-bar-updated'
|
|
|
|
category.save()
|
|
|
|
import_site(copy.deepcopy(payload))
|
|
|
|
assert Category.objects.count() == 2
|
|
|
|
category = Category.objects.latest('pk')
|
|
|
|
assert category.label == 'Foo bar'
|
|
|
|
assert category.slug == 'foo-bar'
|
|
|
|
|
|
|
|
|
2022-04-01 10:13:52 +02:00
|
|
|
def test_import_export_events_type(app):
|
|
|
|
output = get_output_of_command('export_site')
|
|
|
|
payload = json.loads(output)
|
|
|
|
assert len(payload['events_types']) == 0
|
|
|
|
|
|
|
|
events_type = EventsType.objects.create(label='Foo bar')
|
|
|
|
|
|
|
|
output = get_output_of_command('export_site')
|
|
|
|
payload = json.loads(output)
|
|
|
|
assert len(payload['events_types']) == 1
|
|
|
|
|
|
|
|
events_type.delete()
|
|
|
|
assert not EventsType.objects.exists()
|
|
|
|
|
|
|
|
import_site(copy.deepcopy(payload))
|
|
|
|
assert EventsType.objects.count() == 1
|
|
|
|
events_type = EventsType.objects.first()
|
|
|
|
assert events_type.label == 'Foo bar'
|
|
|
|
assert events_type.slug == 'foo-bar'
|
|
|
|
|
|
|
|
# update
|
|
|
|
update_payload = copy.deepcopy(payload)
|
|
|
|
update_payload['events_types'][0]['label'] = 'Foo bar Updated'
|
|
|
|
import_site(update_payload)
|
|
|
|
events_type.refresh_from_db()
|
|
|
|
assert events_type.label == 'Foo bar Updated'
|
|
|
|
|
|
|
|
# insert another events_type
|
|
|
|
events_type.slug = 'foo-bar-updated'
|
|
|
|
events_type.save()
|
|
|
|
import_site(copy.deepcopy(payload))
|
|
|
|
assert EventsType.objects.count() == 2
|
|
|
|
events_type = EventsType.objects.latest('pk')
|
|
|
|
assert events_type.label == 'Foo bar'
|
|
|
|
assert events_type.slug == 'foo-bar'
|
|
|
|
|
|
|
|
|
2022-04-01 14:25:41 +02:00
|
|
|
def test_import_export_resource(app):
|
|
|
|
output = get_output_of_command('export_site')
|
|
|
|
payload = json.loads(output)
|
|
|
|
assert len(payload['resources']) == 0
|
|
|
|
|
|
|
|
resource = Resource.objects.create(label='Foo bar')
|
|
|
|
|
|
|
|
output = get_output_of_command('export_site')
|
|
|
|
payload = json.loads(output)
|
|
|
|
assert len(payload['resources']) == 1
|
|
|
|
|
|
|
|
resource.delete()
|
|
|
|
assert not Resource.objects.exists()
|
|
|
|
|
|
|
|
import_site(copy.deepcopy(payload))
|
|
|
|
assert Resource.objects.count() == 1
|
|
|
|
resource = Resource.objects.first()
|
|
|
|
assert resource.label == 'Foo bar'
|
|
|
|
assert resource.slug == 'foo-bar'
|
|
|
|
|
|
|
|
# update
|
|
|
|
update_payload = copy.deepcopy(payload)
|
|
|
|
update_payload['resources'][0]['label'] = 'Foo bar Updated'
|
|
|
|
import_site(update_payload)
|
|
|
|
resource.refresh_from_db()
|
|
|
|
assert resource.label == 'Foo bar Updated'
|
|
|
|
|
|
|
|
# insert another resource
|
|
|
|
resource.slug = 'foo-bar-updated'
|
|
|
|
resource.save()
|
|
|
|
import_site(copy.deepcopy(payload))
|
|
|
|
assert Resource.objects.count() == 2
|
|
|
|
resource = Resource.objects.latest('pk')
|
|
|
|
assert resource.label == 'Foo bar'
|
|
|
|
assert resource.slug == 'foo-bar'
|
|
|
|
|
|
|
|
|
2021-01-26 10:42:50 +01:00
|
|
|
@mock.patch('chrono.agendas.models.Agenda.is_available_for_simple_management')
|
|
|
|
def test_import_export_desk_simple_management(available_mock):
|
|
|
|
agenda = Agenda.objects.create(label='Foo bar', kind='meetings', desk_simple_management=True)
|
|
|
|
output = get_output_of_command('export_site')
|
|
|
|
payload = json.loads(output)
|
|
|
|
assert len(payload['agendas']) == 1
|
|
|
|
assert payload['agendas'][0]['desk_simple_management'] is True
|
|
|
|
|
|
|
|
# check on creation
|
|
|
|
for available_value in [True, False]:
|
|
|
|
agenda.delete()
|
|
|
|
available_mock.return_value = available_value
|
|
|
|
import_site(payload)
|
|
|
|
agenda = Agenda.objects.latest('pk')
|
|
|
|
assert agenda.desk_simple_management == available_value
|
|
|
|
|
|
|
|
payload['agendas'][0]['desk_simple_management'] = False
|
|
|
|
for available_value in [True, False]:
|
|
|
|
# always ok to set flag to False
|
|
|
|
agenda.delete()
|
|
|
|
available_mock.return_value = available_value
|
|
|
|
import_site(payload)
|
|
|
|
agenda = Agenda.objects.latest('pk')
|
|
|
|
assert agenda.desk_simple_management is False
|
|
|
|
|
|
|
|
# check on update
|
|
|
|
payload['agendas'][0]['desk_simple_management'] = True
|
|
|
|
for available_value in [True, False]:
|
|
|
|
agenda.desk_simple_management = False
|
|
|
|
agenda.save()
|
|
|
|
available_mock.return_value = available_value
|
|
|
|
import_site(payload)
|
|
|
|
agenda.refresh_from_db()
|
|
|
|
assert agenda.desk_simple_management == available_value
|
|
|
|
|
|
|
|
# already True, no change
|
|
|
|
agenda.desk_simple_management = True
|
|
|
|
agenda.save()
|
|
|
|
available_mock.return_value = available_value
|
|
|
|
import_site(payload)
|
|
|
|
agenda.refresh_from_db()
|
|
|
|
assert agenda.desk_simple_management is True
|
|
|
|
|
|
|
|
payload['agendas'][0]['desk_simple_management'] = False
|
|
|
|
for available_value in [True, False]:
|
|
|
|
# always ok to set flag to False
|
|
|
|
for old_value in [True, False]:
|
|
|
|
agenda.desk_simple_management = old_value
|
|
|
|
agenda.save()
|
|
|
|
available_mock.return_value = available_value
|
|
|
|
import_site(payload)
|
|
|
|
agenda.refresh_from_db()
|
|
|
|
assert agenda.desk_simple_management is False
|
|
|
|
|
|
|
|
# not in payload, no changed
|
|
|
|
del payload['agendas'][0]['desk_simple_management']
|
|
|
|
for available_value in [True, False]:
|
|
|
|
for old_value in [True, False]:
|
|
|
|
agenda.desk_simple_management = old_value
|
|
|
|
agenda.save()
|
|
|
|
available_mock.return_value = available_value
|
|
|
|
import_site(payload)
|
|
|
|
agenda.refresh_from_db()
|
|
|
|
assert agenda.desk_simple_management == old_value
|
2021-04-07 13:51:38 +02:00
|
|
|
|
|
|
|
|
|
|
|
def test_export_deleted_meetingtype(app):
|
|
|
|
agenda = Agenda.objects.create(label='Agenda', kind='meetings')
|
|
|
|
meeting_type = MeetingType.objects.create(agenda=agenda, label='Meeting Type', duration=30)
|
|
|
|
|
|
|
|
output = get_output_of_command('export_site')
|
|
|
|
assert len(json.loads(output)['agendas'][0]['meetingtypes']) == 1
|
|
|
|
|
|
|
|
meeting_type.deleted = True
|
|
|
|
meeting_type.save()
|
|
|
|
output = get_output_of_command('export_site')
|
|
|
|
assert len(json.loads(output)['agendas'][0]['meetingtypes']) == 0
|
2021-12-06 16:09:36 +01:00
|
|
|
|
|
|
|
|
2021-12-09 09:48:46 +01:00
|
|
|
def test_import_export_agenda_update(app):
|
|
|
|
agenda = Agenda.objects.create(label='Foo Bar', kind='meetings')
|
|
|
|
|
|
|
|
output = get_output_of_command('export_site')
|
|
|
|
data = json.loads(output)
|
|
|
|
assert len(['agendas']) == 1
|
|
|
|
import_site(data={}, clean=True)
|
|
|
|
|
|
|
|
import_site(data)
|
|
|
|
agenda = Agenda.objects.get()
|
|
|
|
assert agenda.label == 'Foo Bar'
|
|
|
|
|
|
|
|
data['agendas'][0]['label'] = 'Bar Foo'
|
|
|
|
import_site(data)
|
|
|
|
|
|
|
|
agenda = Agenda.objects.get()
|
|
|
|
assert agenda.label == 'Bar Foo'
|
2022-06-28 14:50:00 +02:00
|
|
|
|
|
|
|
|
|
|
|
def test_import_export_shared_custody_settings(app):
|
|
|
|
group = Group.objects.create(name='test')
|
2022-06-28 15:17:57 +02:00
|
|
|
calendar = UnavailabilityCalendar.objects.create(label='Calendar')
|
|
|
|
SharedCustodySettings.objects.create(management_role=group, holidays_calendar=calendar)
|
2022-06-28 14:50:00 +02:00
|
|
|
|
|
|
|
output = get_output_of_command('export_site')
|
|
|
|
import_site(data={}, clean=True)
|
|
|
|
assert SharedCustodySettings.get_singleton().management_role is None
|
|
|
|
Group.objects.all().delete()
|
2022-06-28 15:17:57 +02:00
|
|
|
payload = json.loads(output)
|
|
|
|
del payload['unavailability_calendars']
|
2022-06-28 14:50:00 +02:00
|
|
|
|
|
|
|
with pytest.raises(AgendaImportError) as excinfo:
|
2022-06-28 15:17:57 +02:00
|
|
|
import_site(payload)
|
2022-06-28 14:50:00 +02:00
|
|
|
assert '%s' % excinfo.value == 'Missing roles: "test"'
|
|
|
|
|
|
|
|
group = Group.objects.create(name='test')
|
2022-06-28 15:17:57 +02:00
|
|
|
with pytest.raises(AgendaImportError) as excinfo:
|
|
|
|
import_site(payload)
|
|
|
|
assert '%s' % excinfo.value == 'The unavailability calendar "calendar" does not exist.'
|
|
|
|
|
2022-06-28 14:50:00 +02:00
|
|
|
import_site(json.loads(output))
|
|
|
|
|
|
|
|
settings = SharedCustodySettings.get_singleton()
|
|
|
|
assert settings.management_role == group
|
2022-06-28 15:17:57 +02:00
|
|
|
assert settings.holidays_calendar.slug == calendar.slug
|
2022-06-28 14:50:00 +02:00
|
|
|
|
|
|
|
group2 = Group.objects.create(name='test2')
|
|
|
|
settings.management_role = group2
|
|
|
|
settings.save()
|
|
|
|
|
|
|
|
import_site(json.loads(output))
|
|
|
|
|
|
|
|
settings = SharedCustodySettings.get_singleton()
|
|
|
|
assert settings.management_role == group
|