def handle_places(self, data): base_uri = self.helper.make_proj_uri('PLACE', '') for loc in data.get('locations', []): l = loc.get('location') if l: current = parse_location_name(l, uri_base=self.helper.proj_prefix) place_data = self.helper.make_place(current, base_uri=base_uri) data['places'].append(place_data) note = loc.get('location_note') if note: note = vocab.Note(ident='', content=note) data['referred_to_by'].append(note) date = loc.get('location_date') if date: note = vocab.BibliographyStatement( ident='', content=f'Residence in {l} ({date})') data['referred_to_by'].append(note) address = loc.get('address') if address: contact = model.Identifier(ident='', content=address) contact_data = add_crom_data(data={}, what=contact) data['contact_point'].append(contact_data) note = loc.get('address_note') if note: note = vocab.Note(ident='', content=note) data['referred_to_by'].append(note) date = loc.get('address_date') if date: note = vocab.BibliographyStatement( ident='', content=f'Address at {l} ({date})') data['referred_to_by'].append(note)
def populate_destruction_events(self, data: dict, note, *, type_map, location=None): destruction_types_map = type_map hmo = get_crom_object(data) title = data.get('title') short_title = truncate_with_ellipsis(title, 100) or title r = re.compile( r'[Dd]estroyed(?: (?:by|during) (\w+))?(?: in (\d{4})[.]?)?') m = r.search(note) if m: method = m.group(1) year = m.group(2) # The destruction URI is just the object URI with a suffix. When URIs are # reconciled during prev/post sale rewriting, this will allow us to also reconcile # the URIs for the destructions (of which there should only be one per object) dest_uri = hmo.id + '-Destruction' d = model.Destruction(ident=dest_uri, label=f'Destruction of “{short_title}”') d.referred_to_by = vocab.Note(ident='', content=note) if year is not None: begin, end = date_cleaner(year) ts = timespan_from_outer_bounds(begin, end) ts.identified_by = model.Name(ident='', content=year) d.timespan = ts if method: with suppress(KeyError, AttributeError): type_name = destruction_types_map[method.lower()] otype = vocab.instances[type_name] event = model.Event( label= f'{method.capitalize()} event causing the destruction of “{short_title}”' ) event.classified_as = otype d.caused_by = event data['_events'].append(add_crom_data(data={}, what=event)) if location: current = parse_location_name( location, uri_base=self.helper.uid_tag_prefix) # The place URI used for destruction events is based on the object URI with # a suffix. When URIs are reconciled during prev/post sale rewriting, this # will allow us to also reconcile the URIs for the places of destruction # (of which there should only be one hierarchy per object) base_uri = hmo.id + '-Destruction-Place,' place_data = self.helper.make_place(current, base_uri=base_uri) place = get_crom_object(place_data) if place: data['_locations'].append(place_data) d.took_place_at = place hmo.destroyed_by = d
def handle_places(self, data): locations = {l.strip() for l in data.get('location', '').split(';')} - {''} base_uri = self.helper.make_proj_uri('PLACE', '') for l in locations: current = parse_location_name(l, uri_base=self.helper.proj_prefix) place_data = self.helper.make_place(current, base_uri=base_uri) data['places'].append(place_data) addresses = {l.strip() for l in data.get('address', '').split(';')} - {''} for address in addresses: contact = model.Identifier(ident='', content=address) contact_data = add_crom_data(data={}, what=contact) data['contact_point'].append(contact_data)
def populate_destruction_events(self, data: dict, note, *, type_map, location=None): destruction_types_map = type_map hmo = get_crom_object(data) title = data.get('title') short_title = truncate_with_ellipsis(title, 100) or title r = re.compile( r'[Dd]estroyed(?: (?:by|during) (\w+))?(?: in (\d{4})[.]?)?') m = r.search(note) if m: method = m.group(1) year = m.group(2) dest_id = hmo.id + '-Destr' d = model.Destruction(ident=dest_id, label=f'Destruction of “{short_title}”') d.referred_to_by = vocab.Note(ident='', content=note) if year is not None: begin, end = date_cleaner(year) ts = timespan_from_outer_bounds(begin, end) ts.identified_by = model.Name(ident='', content=year) d.timespan = ts if method: with suppress(KeyError, AttributeError): type_name = destruction_types_map[method.lower()] otype = vocab.instances[type_name] event = model.Event( label= f'{method.capitalize()} event causing the destruction of “{short_title}”' ) event.classified_as = otype d.caused_by = event data['_events'].append(add_crom_data(data={}, what=event)) if location: current = parse_location_name( location, uri_base=self.helper.uid_tag_prefix) base_uri = hmo.id + '-Place,' place_data = self.helper.make_place(current, base_uri=base_uri) place = get_crom_object(place_data) if place: data['_locations'].append(place_data) d.took_place_at = place hmo.destroyed_by = d
def model_sojourn(self, data, loc): base_uri = self.helper.make_proj_uri('PLACE', '') cb = data.get('corporate_body', False) sojourn_type = vocab.Establishment if cb else vocab.Residing sdata = { 'type': sojourn_type, 'referred_to_by': [], } verbatim_date = loc.get('address_date') if verbatim_date: date_range = date_cleaner(verbatim_date) if date_range: begin, end = date_range ts = timespan_from_outer_bounds(*date_range) ts.identified_by = model.Name(ident='', content=verbatim_date) sdata['timespan'] = add_crom_data( { 'address_date': verbatim_date, 'begin': begin, 'end': end }, ts) current = None l = loc.get('location') if l: current = parse_location_name(l, uri_base=self.helper.proj_prefix) address = loc.get('address') if address: current = { 'name': address, 'part_of': current, 'type': 'address', } for k in ('address_note', 'location_note'): note = loc.get(k) if note: sdata['referred_to_by'].append( vocab.Note(ident='', content=note)) if current: place_data = self.helper.make_place(current, base_uri=base_uri) data['_places'].append(place_data) sdata['place'] = place_data return sdata
def _populate_object_present_location(self, data: dict, now_key, destruction_types_map): hmo = get_crom_object(data) location = data.get('present_location') if location: loc = location.get('geog') note = location.get('note') if loc: if 'destroyed ' in loc.lower(): self.populate_destruction_events( data, loc, type_map=destruction_types_map) elif isinstance(note, str) and 'destroyed ' in note.lower(): # the object was destroyed, so any "present location" data is actually # an indication of the location of destruction. self.populate_destruction_events( data, note, type_map=destruction_types_map, location=loc) else: # TODO: if `parse_location_name` fails, still preserve the location string somehow current = parse_location_name( loc, uri_base=self.helper.uid_tag_prefix) inst = location.get('inst') if inst: owner_data = { 'label': f'{inst} ({loc})', 'identifiers': [model.Name(ident='', content=inst)] } ulan = None with suppress(ValueError, TypeError): ulan = int(location.get('insi')) if ulan: owner_data['ulan'] = ulan owner_data['uri'] = self.helper.make_proj_uri( 'ORG', 'ULAN', ulan) else: owner_data['uri'] = self.helper.make_proj_uri( 'ORG', 'NAME', inst, 'PLACE', loc) else: owner_data = { 'label': '(Anonymous organization)', 'uri': self.helper.make_proj_uri('ORG', 'CURR-OWN', *now_key), } if note: owner_data['note'] = note base_uri = hmo.id + '-Place,' place_data = self.helper.make_place(current, base_uri=base_uri) place = get_crom_object(place_data) make_la_org = pipeline.linkedart.MakeLinkedArtOrganization( ) owner_data = make_la_org(owner_data) owner = get_crom_object(owner_data) acc = location.get('acc') if acc: acc_number = vocab.AccessionNumber(ident='', content=acc) hmo.identified_by = acc_number assignment = model.AttributeAssignment(ident='') assignment.carried_out_by = owner acc_number.assigned_by = assignment owner.residence = place data['_locations'].append(place_data) data['_final_org'] = owner_data else: pass # there is no present location place string
def handle_prev_post_owner(self, data, hmo, tx_data, sale_type, lot_object_key, owner_record, record_id, rev, ts=None, make_label=None): current_tx = get_crom_object(tx_data) sales_record = get_crom_object(data['_record']) if rev: rel = f'leading to the previous ownership of' source_label = 'Source of information on history of the object prior to the current sale.' else: rel = f'leading to the subsequent ownership of' source_label = 'Source of information on history of the object after the current sale.' owner_record.update({ 'pi_record_no': data['pi_record_no'], 'ulan': owner_record.get('ulan', owner_record.get('own_ulan')), }) self.add_person(owner_record, record=sales_record, relative_id=record_id, role='artist') owner = get_crom_object(owner_record) # TODO: handle other fields of owner_record: own_auth_d, own_auth_q, own_ques, own_so if owner_record.get('own_auth_l'): loc = owner_record['own_auth_l'] current = parse_location_name(loc, uri_base=self.helper.uid_tag_prefix) place_data = self.helper.make_place(current) place = get_crom_object(place_data) owner.residence = place data['_owner_locations'].append(place_data) if owner_record.get('own_auth_p'): content = owner_record['own_auth_p'] owner.referred_to_by = vocab.Note(ident='', content=content) data.setdefault('_other_owners', []) data['_other_owners'].append(owner_record) # The Provenance Entry URI must not share a prefix with the object URI, otherwise # we run the rist of provenance entries being accidentally merged during URI # reconciliation as part of the prev/post sale rewriting. tx_uri = self.helper.prepend_uri_key(hmo.id, f'PROV-{record_id}') tx_label_args = tuple([self.helper, sale_type, 'Sold', rel] + list(lot_object_key)) tx, _ = self.related_procurement(hmo, tx_label_args, current_tx, ts, buyer=owner, previous=rev, ident=tx_uri, make_label=make_label) if owner_record.get('own_auth_e'): content = owner_record['own_auth_e'] tx.referred_to_by = vocab.Note(ident='', content=content) own_info_source = owner_record.get('own_so') if own_info_source: note = vocab.SourceStatement(ident='', content=own_info_source, label=source_label) tx.referred_to_by = note ptx_data = tx_data.copy() data['_prov_entries'].append(add_crom_data(data=ptx_data, what=tx))
def _populate_object_present_location(self, data: dict, now_key, destruction_types_map): hmo = get_crom_object(data) location = data.get('present_location') if location: loc = location.get('geog') note = location.get('note') # in these two if blocks, the object was destroyed, so any "present location" # data is actually an indication of the location of destruction. if isinstance(loc, str) and 'destroyed ' in loc.lower(): self.populate_destruction_events( data, loc, type_map=destruction_types_map) loc = None elif isinstance(note, str) and 'destroyed ' in note.lower(): self.populate_destruction_events( data, note, type_map=destruction_types_map, location=loc) note = None if loc: # TODO: if `parse_location_name` fails, still preserve the location string somehow current = parse_location_name( loc, uri_base=self.helper.uid_tag_prefix) inst = location.get('inst') if inst: owner_data = { 'label': f'{inst} ({loc})', 'identifiers': [model.Name(ident='', content=inst)] } ulan = None with suppress(ValueError, TypeError): ulan = int(location.get('insi')) if ulan: owner_data['ulan'] = ulan owner_data['uri'] = self.helper.make_proj_uri( 'ORG', 'ULAN', ulan) else: owner_data['uri'] = self.helper.make_proj_uri( 'ORG', 'NAME', inst, 'PLACE', loc) else: owner_data = { 'label': '(Anonymous organization)', 'uri': self.helper.make_proj_uri('ORG', 'CURR-OWN', *now_key), } if note: owner_data['note'] = note # It's conceivable that there could be more than one "present location" # for an object that is reconciled based on prev/post sale rewriting. # Therefore, the place URI must not share a prefix with the object URI, # otherwise all such places are liable to be merged during URI # reconciliation as part of the prev/post sale rewriting. base_uri = self.helper.prepend_uri_key(hmo.id, 'PLACE') place_data = self.helper.make_place(current, base_uri=base_uri) place = get_crom_object(place_data) make_la_org = pipeline.linkedart.MakeLinkedArtOrganization() owner_data = make_la_org(owner_data) owner = get_crom_object(owner_data) acc = location.get('acc') if acc: acc_number = vocab.AccessionNumber(ident='', content=acc) hmo.identified_by = acc_number assignment = model.AttributeAssignment(ident='') assignment.carried_out_by = owner acc_number.assigned_by = assignment owner.residence = place data['_locations'].append(place_data) data['_final_org'] = owner_data else: pass # there is no present location place string
def handle_prev_post_owner(self, data, hmo, tx_data, sale_type, lot_object_key, owner_record, record_id, rev, ts=None, make_label=None): current_tx = get_crom_object(tx_data) sales_record = get_crom_object(data['_record']) if rev: rel = f'leading to the previous ownership of' source_label = 'Source of information on history of the object prior to the current sale.' else: rel = f'leading to the subsequent ownership of' source_label = 'Source of information on history of the object after the current sale.' owner_record.update({ 'pi_record_no': data['pi_record_no'], 'ulan': owner_record.get('ulan', owner_record.get('own_ulan')), 'auth_name': owner_record.get('auth_name', owner_record.get('own_auth')), 'name': owner_record.get('name', owner_record.get('own')), }) self.add_person(owner_record, record=sales_record, relative_id=record_id, role='artist') owner = get_crom_object(owner_record) # TODO: handle other fields of owner_record: own_auth_d, own_auth_q, own_ques, own_so if owner_record.get('own_auth_l'): loc = owner_record['own_auth_l'] current = parse_location_name(loc, uri_base=self.helper.uid_tag_prefix) place_data = self.helper.make_place(current) place = get_crom_object(place_data) owner.residence = place data['_owner_locations'].append(place_data) data.setdefault('_other_owners', []) data['_other_owners'].append(owner_record) tx_uri = hmo.id + f'-{record_id}-Prov' tx_label_args = tuple([self.helper, sale_type, 'Sold', rel] + list(lot_object_key)) tx, _ = self.related_procurement(hmo, tx_label_args, current_tx, ts, buyer=owner, previous=rev, ident=tx_uri, make_label=make_label) own_info_source = owner_record.get('own_so') if own_info_source: note = vocab.SourceStatement(ident='', content=own_info_source, label=source_label) tx.referred_to_by = note ptx_data = tx_data.copy() data['_prov_entries'].append(add_crom_data(data=ptx_data, what=tx))