diff --git a/SAS/TMSS/src/tmss/tmssapp/migrations/0001_initial.py b/SAS/TMSS/src/tmss/tmssapp/migrations/0001_initial.py index a657a6531ec6a608c64768ac2905a436e20bec7d..ced2c63713eb38fcf027a7a7b84f9bb6a35de65f 100644 --- a/SAS/TMSS/src/tmss/tmssapp/migrations/0001_initial.py +++ b/SAS/TMSS/src/tmss/tmssapp/migrations/0001_initial.py @@ -1,4 +1,4 @@ -# Generated by Django 3.0.9 on 2020-11-30 08:59 +# Generated by Django 3.0.9 on 2020-12-03 09:59 from django.conf import settings import django.contrib.postgres.fields @@ -428,7 +428,7 @@ class Migration(migrations.Migration): ('name', models.CharField(help_text='Human-readable name of this object.', max_length=128)), ('description', models.CharField(help_text='Short description for this reservation, used in overviews', max_length=255)), ('start_time', models.DateTimeField(help_text='Start of this reservation.')), - ('duration', models.IntegerField(help_text='Duration of this reservations.', null=True)), + ('duration', models.IntegerField(help_text='Duration of this reservation (in seconds). If null, then this reservation is indefinitely.', null=True)), ('specifications_doc', django.contrib.postgres.fields.jsonb.JSONField(help_text='Properties of this reservation')), ], options={ @@ -1200,7 +1200,7 @@ class Migration(migrations.Migration): migrations.AddField( model_name='reservation', name='project', - field=models.ForeignKey(help_text='Reservation will be accounted for this project.', on_delete=django.db.models.deletion.CASCADE, related_name='reservations', to='tmssapp.Project'), + field=models.ForeignKey(help_text='Reservation will be accounted for this project.', null=True, on_delete=django.db.models.deletion.CASCADE, related_name='reservations', to='tmssapp.Project'), ), migrations.AddField( model_name='reservation', @@ -1473,4 +1473,4 @@ class Migration(migrations.Migration): model_name='dataproduct', index=django.contrib.postgres.indexes.GinIndex(fields=['tags'], name='tmssapp_dat_tags_5932a3_gin'), ), - ] \ No newline at end of file + ] diff --git a/SAS/TMSS/src/tmss/tmssapp/models/specification.py b/SAS/TMSS/src/tmss/tmssapp/models/specification.py index 1f5a6e3b5be0631f4c5b99ee9e4b6a2176556623..b3629f35cfd18d93ccf77af17911b7f9928271cd 100644 --- a/SAS/TMSS/src/tmss/tmssapp/models/specification.py +++ b/SAS/TMSS/src/tmss/tmssapp/models/specification.py @@ -385,34 +385,6 @@ class DefaultReservationTemplate(BasicCommon): template = ForeignKey("ReservationTemplate", on_delete=PROTECT) -# -# DatabaseView objects -# -class TaskBlueprintSummary(Model): - taskblueprint_id = IntegerField() - subtask_id = IntegerField() - substate = CharField(max_length=128) - subtask_type = CharField(max_length=128) - - class Meta: - managed = False - db_table = 'tmssapp_taskblueprintsummary' - - -class SchedulingUnitBlueprintSummary(Model): - # Using in an id and ForeignKey is not common for a view BUT the id is a 'dummy' to be able to use in Django - # https://resources.rescale.com/using-database-views-in-django-orm/ - # otherwise an exception will be thrown - id = IntegerField(primary_key=True) - sub_id = IntegerField() - taskblueprint_id = IntegerField() - task_type = CharField(max_length=128) - derived_task_status = CharField(max_length=128) - - class Meta: - managed = False - db_table = 'tmssapp_schedulingunitblueprintsummary' - # # Instance Objects # @@ -1124,13 +1096,20 @@ class TaskSchedulingRelationDraft(BasicCommon): class Reservation(NamedCommon): - project = ForeignKey('Project', related_name='reservations', on_delete=CASCADE, help_text='Reservation will be accounted for this project.') + project = ForeignKey('Project', null=True, related_name='reservations', on_delete=CASCADE, help_text='Reservation will be accounted for this project.') description = CharField(max_length=255, help_text='Short description for this reservation, used in overviews') start_time = DateTimeField(help_text='Start of this reservation.') - duration = IntegerField(null=True, help_text='Duration of this reservations.') + duration = IntegerField(null=True, help_text='Duration of this reservation (in seconds). If null, then this reservation is indefinitely.') specifications_doc = JSONField(help_text='Properties of this reservation') specifications_template = ForeignKey('ReservationTemplate', on_delete=CASCADE, help_text='Schema used for specifications_doc.') + @property + def stop_time(self) -> datetime.datetime: + '''The stop_time based on start_time+duration if duration is known, else None''' + if self.duration: + return self.start_time + datetime.timedelta(seconds=self.duration) + return None + def save(self, force_insert=False, force_update=False, using=None, update_fields=None): annotate_validate_add_defaults_to_doc_using_template(self, 'specifications_doc', 'specifications_template') super().save(force_insert, force_update, using, update_fields) diff --git a/SAS/TMSS/src/tmss/tmssapp/serializers/specification.py b/SAS/TMSS/src/tmss/tmssapp/serializers/specification.py index 19afb2076dfec6e7b2644021680e1750d90db36e..55eab8b6118553a53fd2ec6f9e4e9b15cf405532 100644 --- a/SAS/TMSS/src/tmss/tmssapp/serializers/specification.py +++ b/SAS/TMSS/src/tmss/tmssapp/serializers/specification.py @@ -399,6 +399,9 @@ class DefaultReservationTemplateSerializer(RelationalHyperlinkedModelSerializer) class ReservationSerializer(RelationalHyperlinkedModelSerializer): + specifications_doc = JSONEditorField(schema_source='specifications_template.schema') + class Meta: model = models.Reservation fields = '__all__' + extra_fields = ['stop_time']