Coverage for toardb/timeseries/models_core.py: 100%

35 statements  

« prev     ^ index     » next       coverage.py v7.11.0, created at 2025-11-03 20:32 +0000

1# SPDX-FileCopyrightText: 2021 Forschungszentrum Jülich GmbH 

2# SPDX-License-Identifier: MIT 

3 

4""" 

5class Timeseries (Base) 

6======================= 

7""" 

8from sqlalchemy import Column, DateTime, Float, ForeignKey, Integer, text, String, \ 

9 Text, CheckConstraint, UniqueConstraint, PrimaryKeyConstraint, \ 

10 Sequence 

11from sqlalchemy.orm import relationship 

12from sqlalchemy.dialects.postgresql import JSONB 

13from toardb.stationmeta.models import StationmetaCore 

14from toardb.variables.models import Variable 

15from .models_programme import TimeseriesProgramme 

16from toardb.base import Base 

17 

18 

19TIMESERIES_ID_SEQ = Sequence('timeseries_id_seq') # define sequence explicitly 

20class Timeseries(Base): 

21 """ 

22 Table "public.timeseries" 

23 

24 +------------------------------+--------------------------+-----------+----------+----------------------------------------+ 

25 | Column | Type | Collation | Nullable | Default | 

26 +==============================+==========================+===========+==========+========================================+ 

27 | id | integer | | not null | nextval('timeseries_id_seq'::regclass) | 

28 +------------------------------+--------------------------+-----------+----------+----------------------------------------+ 

29 | label | character varying(128) | | not null | | 

30 +------------------------------+--------------------------+-----------+----------+----------------------------------------+ 

31 | order | integer | | not null | | 

32 +------------------------------+--------------------------+-----------+----------+----------------------------------------+ 

33 | sampling_frequency | integer | | not null | | 

34 +------------------------------+--------------------------+-----------+----------+----------------------------------------+ 

35 | aggregation | integer | | not null | | 

36 +------------------------------+--------------------------+-----------+----------+----------------------------------------+ 

37 | data_start_date | timestamp with time zone | | not null | '2050-01-01 00:00:00' | 

38 +------------------------------+--------------------------+-----------+----------+----------------------------------------+ 

39 | data_end_date | timestamp with time zone | | not null | '1900-01-01 00:00:00' | 

40 +------------------------------+--------------------------+-----------+----------+----------------------------------------+ 

41 | data_origin_type | integer | | not null | 0 | 

42 +------------------------------+--------------------------+-----------+----------+----------------------------------------+ 

43 | data_origin | integer | | not null | 0 | 

44 +------------------------------+--------------------------+-----------+----------+----------------------------------------+ 

45 | sampling_height | double precision | | not null | | 

46 +------------------------------+--------------------------+-----------+----------+----------------------------------------+ 

47 | additional_metadata | jsonb | | not null | | 

48 +------------------------------+--------------------------+-----------+----------+----------------------------------------+ 

49 | provider_version | character varying(28) | | not null | 'NA' | 

50 +------------------------------+--------------------------+-----------+----------+----------------------------------------+ 

51 | latest_version | character varying(28) | | not null | '000001.000000.00000000000000' | 

52 +------------------------------+--------------------------+-----------+----------+----------------------------------------+ 

53 | data_license_accepted | timestamp with time zone | | not null | '1900-01-01' | 

54 +------------------------------+--------------------------+-----------+----------+----------------------------------------+ 

55 | dataset_approved_by_provider | timestamp with time zone | | not null | '1900-01-01' | 

56 +------------------------------+--------------------------+-----------+----------+----------------------------------------+ 

57 | station_id | integer | | not null | | 

58 +------------------------------+--------------------------+-----------+----------+----------------------------------------+ 

59 | variable_id | integer | | not null | | 

60 +------------------------------+--------------------------+-----------+----------+----------------------------------------+ 

61 | programme_id | integer | | not null | 0 | 

62 +------------------------------+--------------------------+-----------+----------+----------------------------------------+ 

63 | doi | character varying(64) | | not null | '' | 

64 +------------------------------+--------------------------+-----------+----------+----------------------------------------+ 

65 | coverage | double precision | | not null | -1.0 | 

66 +------------------------------+--------------------------+-----------+----------+----------------------------------------+ 

67 

68 Indexes: 

69 "timeseries_pkey" PRIMARY KEY, btree (id) 

70 "timeseries_station_id" btree (station_id) 

71 "timeseries_variable_id" btree (variable_id) 

72 Check constraints: 

73 "timeseries_aggregation_check" CHECK (aggregation >= 0) 

74 "timeseries_order_check" CHECK ("order" >= 0) 

75 "timeseries_sampling_frequency_check" CHECK (sampling_frequency >= 0) 

76 Foreign-key constraints: 

77 "timeseries_station_id_fk_stationmeta_core_id" FOREIGN KEY (station_id) REFERENCES stationmeta_core(id) DEFERRABLE INITIALLY DEFERRED 

78 "timeseries_variable_id_fk_variables_id" FOREIGN KEY (variable_id) REFERENCES variables(id) DEFERRABLE INITIALLY DEFERREDForeign-key constraints: 

79 "timeseries_aggregation_fk_at_vocabulary_enum_val" FOREIGN KEY (aggregation) REFERENCES at_vocabulary(enum_val) 

80 "timeseries_sampling_frequency_fk_sf_vocabulary_enum_val" FOREIGN KEY (sampling_frequency) REFERENCES sf_vocabulary(enum_val) 

81 "timeseries_data_origin_fk_do_vocabulary_enum_val" FOREIGN KEY (data_origin) REFERENCES do_vocabulary(enum_val) 

82 "timeseries_data_origin_type_fk_ot_vocabulary_enum_val" FOREIGN KEY (data_origin_type) REFERENCES ot_vocabulary(enum_val) 

83 "timeseries_programme_id_fk_timeseries_programmes_id" FOREIGN KEY (programme_id) REFERENCES timeseries_programmes(id) 

84 Referenced by: 

85 TABLE "data" CONSTRAINT "data_timeseries_id_fk_timeseries_id" FOREIGN KEY (timeseries_id) REFERENCES timeseries(id) DEFERRABLE INITIALLY DEFERRED 

86 TABLE "timeseries_timeseries_annotations" CONSTRAINT "timeseries_timeseries_annotations_timeseries_id_fk_timeseries_id" FOREIGN KEY (timeseries_id) REFERENCES timeseries(id) DEFERRABLE INITIALLY DEFERRED 

87 TABLE "timeseries_timeseries_roles" CONSTRAINT "timeseries_timeseries_roles_timeseries_id_fk_timeseries_id" FOREIGN KEY (timeseries_id) REFERENCES timeseries(id) DEFERRABLE INITIALLY DEFERRED 

88 TABLE "timeseries_timeseries_programmes" CONSTRAINT "timeseries_timeseries_programmes_timeseries_id_fk_timeseries_id" FOREIGN KEY (timeseries_id) REFERENCES timeseries(id) DEFERRABLE INITIALLY DEFERRED 

89 """ 

90 

91 __tablename__ = 'timeseries' 

92 __table_args__ = ( 

93 CheckConstraint('"order" >= 0'), 

94 CheckConstraint('aggregation >= 0'), 

95 CheckConstraint('sampling_frequency >= 0'), 

96 UniqueConstraint('station_id', 'variable_id', 'label'), 

97 ) 

98 

99 id = Column(Integer, TIMESERIES_ID_SEQ, primary_key=True, server_default=TIMESERIES_ID_SEQ.next_value()) 

100 label = Column(String(128), nullable=False) 

101 order = Column(Integer, nullable=False) 

102 sampling_frequency = Column(ForeignKey('sf_vocabulary.enum_val'), nullable=False) 

103 aggregation = Column(ForeignKey('at_vocabulary.enum_val'), nullable=False) 

104 data_start_date = Column(DateTime(True), nullable=False) 

105 data_end_date = Column(DateTime(True), nullable=False) 

106 data_origin_type = Column(ForeignKey('ot_vocabulary.enum_val'), nullable=False, server_default=text("0")) 

107 data_origin = Column(ForeignKey('do_vocabulary.enum_val'), nullable=False, server_default=text("0")) 

108 sampling_height = Column(Float(53), nullable=False) 

109 provider_version = Column(String(28), nullable=False, server_default=text("'NA'")) 

110 latest_version = Column(String(28), nullable=False, server_default=text("'000001.000000.00000000000000'")) 

111 data_license_accepted = Column(DateTime(True), nullable=False, server_default=text("'1900-01-01 00:00:00+00'::timestamp with time zone")) 

112 dataset_approved_by_provider = Column(DateTime(True), nullable=False, server_default=text("'1900-01-01 00:00:00+00'::timestamp with time zone")) 

113# do not use string declaration here (not working for pytest) 

114# use the explicit class name here, 

115# see: https://groups.google.com/forum/#!topic/sqlalchemy/YjGhE4d6K4U 

116 station_id = Column(ForeignKey(StationmetaCore.id, deferrable=True, initially='DEFERRED'), nullable=False, index=True) 

117 variable_id = Column(ForeignKey(Variable.id, deferrable=True, initially='DEFERRED'), nullable=False, index=True) 

118 programme_id = Column(ForeignKey(TimeseriesProgramme.id, deferrable=True, initially='DEFERRED'), nullable=False, server_default=text("0")) 

119 doi = Column(String(64), nullable=False, server_default=text("'000001.000000.00000000000000'")) 

120 coverage = Column(Float, nullable=False, server_default=text('-1.0')) 

121 

122 # for the nested view 

123 # problems with station and coordinates in nested views!!! 

124 station = relationship('StationmetaCore') 

125 variable = relationship('Variable') 

126 programme = relationship('TimeseriesProgramme') 

127 changelog = relationship('TimeseriesChangelog', back_populates='timeseries') 

128 

129 additional_metadata = Column(JSONB(astext_type=Text()), nullable=True) 

130