def __init__( self, source_asset_or_uid: Union['kpi.models.Asset', str], filename: str, fields: list, asset: 'kpi.models.Asset', paired_data_uid: str = None, ): """ Usually, this constructor should NOT be called directly except when creating a new paired data relationship. To retrieve existing pairings, use `PairedData.objects(asset)` instead. When the submission data from `source_asset_or_uid` is collected into a single XML file, it is attached to `asset` using `filename`, which the content of `asset` can then reference via `xml-external` (see https://xlsform.org/en/#external-xml-data). Specify a list of fields from the source asset to include using `fields`, or pass an empty list to include all fields. """ try: self.source_uid = source_asset_or_uid.uid except AttributeError: self.source_uid = source_asset_or_uid self.asset = asset self.filename = filename self.fields = fields if not paired_data_uid: self.paired_data_uid = KpiUidField.generate_unique_id('pd') else: self.paired_data_uid = paired_data_uid self._asset_file = None
def save(self, **kwargs): # When PairedData objects are synchronize by back-end deployment class # (i.e.: `sync_media_files()` is triggered), the back-end deployment class # also updates the boolean `synced_with_backend`. We must handle this # over here before going further to avoid calling `Asset.save()` # which would call `sync_media_files()` again, # which would make us enter an infinite loop. try: update_fields = kwargs['update_fields'] except KeyError: pass else: if 'synced_with_backend' in update_fields: AssetFile.objects.filter(uid=self.paired_data_uid).update( synced_with_backend=self.synced_with_backend ) return try: self.asset.paired_data[self.source_uid]['paired_data_uid'] # self.paired_data_uid would have been set when `objects()` # calls the constructor except KeyError: self.paired_data_uid = KpiUidField.generate_unique_id('pd') self.asset.paired_data[self.source_uid] = { 'fields': self.fields, 'filename': self.filename, 'paired_data_uid': self.paired_data_uid, } self.asset.save( update_fields=['paired_data'], adjust_content=False, create_version=False, )