예제 #1
0
파일: test_vocab.py 프로젝트: thegetty/crom
	def test_multitype(self):
		from cromulent.vocab import make_multitype_obj, Painting, Drawing
		inst = make_multitype_obj(Painting, Drawing)
		self.assertTrue(isinstance(inst, Painting))
		self.assertTrue(len(inst.classified_as) == 2)
		self.assertTrue(inst.classified_as[1].id == "http://vocab.getty.edu/aat/300033973")

		from cromulent.model import HumanMadeObject

		inst = make_multitype_obj(HumanMadeObject, Painting)
		self.assertTrue(len(inst.classified_as) == 1)
		self.assertTrue(inst.classified_as[0].id == "http://vocab.getty.edu/aat/300033618")
예제 #2
0
def add_object_type(data, vocab_type_map):
    '''Add appropriate type information for an object based on its 'object_type' name'''
    typestring = data.get('object_type', '')
    if typestring in vocab_type_map:
        clsname = vocab_type_map.get(typestring, None)
        otype = getattr(vocab, clsname)
        add_crom_data(data=data, what=otype(ident=data['uri']))
    elif ';' in typestring:
        parts = [s.strip() for s in typestring.split(';')]
        if all([s in vocab_type_map for s in parts]):
            types = [getattr(vocab, vocab_type_map[s]) for s in parts]
            obj = vocab.make_multitype_obj(*types, ident=data['uri'])
            add_crom_data(data=data, what=obj)
        else:
            warnings.warn(
                f'*** Not all object types matched for {typestring!r}')
            add_crom_data(data=data,
                          what=model.HumanMadeObject(ident=data['uri']))
    else:
        warnings.warn(f'*** No object type for {typestring!r}')
        add_crom_data(data=data, what=model.HumanMadeObject(ident=data['uri']))

    parent = data['parent_data']
    coll_data = parent.get('_lot_object_set')
    if coll_data:
        coll = get_crom_object(coll_data)
        if coll:
            data['member_of'] = [coll]

    return data
예제 #3
0
파일: __init__.py 프로젝트: kasei/pipeline
    def professional_activity(self,
                              name: str,
                              century=None,
                              date_range=None,
                              classified_as=None,
                              **kwargs):
        '''
		Return a vocab.Active object representing the professional activities
		of the `name`d person.
		
		If `century` or `date_range` arguments are supplied, they are used to
		associate a timespan with the activity.
		
		If a `classified_as` list is supplied, it is used to further classify
		the `vocab.Active` object.
		'''
        if classified_as:
            classified_as.append(vocab.Active)
        else:
            classified_as = [vocab.Active]

        args = {'ident': '', 'label': f'Professional activity of {name}'}
        if 'ident' in kwargs:
            args['ident'] = kwargs['ident']
        a = vocab.make_multitype_obj(*classified_as, **args)

        ts = self.active_timespan(century=century,
                                  date_range=date_range,
                                  **kwargs)
        if ts:
            a.timespan = ts
        return a
예제 #4
0
    def __call__(self, data: dict, non_auctions):
        '''Add modeling for auction catalogs as linguistic objects'''
        cno = data['auction_of_lot']['catalog_number']
        rec_num = data['pi_record_no']
        record_uri = self.helper.make_proj_uri('CATALOG', cno, 'RECORD',
                                               rec_num)
        record = vocab.ParagraphText(
            ident=record_uri,
            label=f'Sale recorded in catalog (record number {rec_num})')
        data['_sale_record'] = add_crom_data({'uri': record_uri}, record)

        page_id = data.get('pg')
        pdf_page_id = data.get('ppg')
        if not page_id:
            yield data
            return

        sale_type = non_auctions.get(cno, data.get('non_auction_flag'))
        if sale_type:
            non_auctions[cno] = sale_type
        sale_type = sale_type or 'Auction'
        catalog = self.helper.catalog_text(cno, sale_type)

        cdata = add_crom_data(data={'uri': catalog.id}, what=catalog)
        idents = [
            vocab.PageNumber(ident='', content=page_id),
        ]
        if pdf_page_id:
            idents.append(
                vocab.make_multitype_obj(vocab.PageNumber,
                                         vocab.OrderNumber,
                                         ident='',
                                         content=pdf_page_id,
                                         label=f'Page Order'))
        data['_text_page'] = {
            'uri': self.helper.make_proj_uri('CATALOG', cno, 'Page', page_id),
            'object_type': vocab.PageTextForm,
            'label': f'Sale Catalog {cno}, Page {page_id}',
            'identifiers': idents,
            'referred_to_by': [],
            'part_of': [cdata],
            'part': [],
        }

        mlo = MakeLinkedArtLinguisticObject()
        mlo(data['_text_page'])

        yield data
예제 #5
0
    def __call__(self, data: dict):
        if '_LOD_OBJECT' in data:
            thing = data['_LOD_OBJECT']
        else:
            otype = data['object_type']
            otypes = otype if isinstance(otype, list) else [otype]
            kwargs = {}
            if 'uri' in data:
                kwargs['ident'] = data['uri']
            elif 'uuid' in data:
                kwargs['ident'] = "urn:uuid:%s" % data['uuid']
            else:
                raise Exception(
                    'MakeLinkedArtRecord called with a dictionary with neither uuid or uri member'
                )
            thing = vocab.make_multitype_obj(*otypes, **kwargs)

        self.set_properties(data, thing)

        return add_crom_data(data=data, what=thing)
예제 #6
0
    def __call__(self, data: dict, *, attribution_modifiers,
                 attribution_group_types):
        '''Add modeling for artists as people involved in the production of an object'''
        hmo = get_crom_object(data)
        data['_organizations'] = []
        data['_original_objects'] = []

        try:
            hmo_label = f'{hmo._label}'
        except AttributeError:
            hmo_label = 'object'
        event_id = hmo.id + '-Prod'
        event = model.Production(ident=event_id,
                                 label=f'Production event for {hmo_label}')
        hmo.produced_by = event

        artists = data.get('_artists', [])

        sales_record = get_crom_object(data['_record'])
        pi = self.helper.person_identity

        for a in artists:
            a.setdefault('referred_to_by', [])
            a.update({
                'pi_record_no': data['pi_record_no'],
                'ulan': a['artist_ulan'],
                'auth_name': a['art_authority'],
                'name': a['artist_name']
            })
            if a.get('biography'):
                bio = a['biography']
                del a['biography']
                cite = vocab.BiographyStatement(ident='', content=bio)
                a['referred_to_by'].append(cite)

        def is_or_anon(data: dict):
            if pi.is_anonymous(data):
                mods = {
                    m.lower().strip()
                    for m in data.get('attrib_mod_auth', '').split(';')
                }
                return 'or' in mods
            return False

        or_anon_records = [is_or_anon(a) for a in artists]
        uncertain_attribution = any(or_anon_records)
        for seq_no, a in enumerate(artists):
            attribute_assignment_id = event.id + f'-artist-assignment-{seq_no}'
            if is_or_anon(a):
                # do not model the "or anonymous" records; they turn into uncertainty on the other records
                continue
            person = self.helper.add_person(a,
                                            record=sales_record,
                                            relative_id=f'artist-{seq_no+1}',
                                            role='artist')
            artist_label = a.get('role_label')

            mod = a.get('attrib_mod_auth', '')
            mods = CaseFoldingSet({m.strip() for m in mod.split(';')} - {''})
            attrib_assignment_classes = [model.AttributeAssignment]

            if uncertain_attribution or 'or' in mods:
                attrib_assignment_classes.append(vocab.PossibleAssignment)

            if mods:
                # TODO: this should probably be in its own JSON service file:
                STYLE_OF = attribution_modifiers['style of']
                FORMERLY_ATTRIBUTED_TO = attribution_modifiers[
                    'formerly attributed to']
                ATTRIBUTED_TO = attribution_modifiers['attributed to']
                COPY_AFTER = attribution_modifiers['copy after']
                PROBABLY = attribution_modifiers['probably by']
                POSSIBLY = attribution_modifiers['possibly by']
                UNCERTAIN = attribution_modifiers['uncertain']

                GROUP_TYPES = set(attribution_group_types.values())
                GROUP_MODS = {
                    k
                    for k, v in attribution_group_types.items()
                    if v in GROUP_TYPES
                }

                if 'copy by' in mods:
                    # equivalent to no modifier
                    pass
                elif ATTRIBUTED_TO.intersects(mods):
                    # equivalent to no modifier
                    pass
                elif STYLE_OF.intersects(mods):
                    assignment = vocab.make_multitype_obj(
                        *attrib_assignment_classes,
                        ident=attribute_assignment_id,
                        label=f'In the style of {artist_label}')
                    event.attributed_by = assignment
                    assignment.assigned_property = 'influenced_by'
                    assignment.property_classified_as = vocab.instances[
                        'style of']
                    assignment.assigned = person
                    continue
                elif mods.intersects(GROUP_MODS):
                    mod_name = list(GROUP_MODS
                                    & mods)[0]  # TODO: use all matching types?
                    clsname = attribution_group_types[mod_name]
                    cls = getattr(vocab, clsname)
                    group_label = f'{clsname} of {artist_label}'
                    group_id = a['uri'] + f'-{clsname}'
                    group = cls(ident=group_id, label=group_label)
                    formation = model.Formation(
                        ident='', label=f'Formation of {group_label}')
                    formation.influenced_by = person
                    group.formed_by = formation
                    group_data = add_crom_data({'uri': group_id}, group)
                    data['_organizations'].append(group_data)

                    subevent_id = event_id + f'-{seq_no}'  # TODO: fix for the case of post-sales merging
                    subevent = model.Production(
                        ident=subevent_id,
                        label=f'Production sub-event for {group_label}')
                    subevent.carried_out_by = group

                    if uncertain_attribution:
                        assignment = vocab.make_multitype_obj(
                            *attrib_assignment_classes,
                            ident=attribute_assignment_id,
                            label=f'Possibly attributed to {group_label}')
                        event.attributed_by = assignment
                        assignment.assigned_property = 'part'
                        assignment.assigned = subevent
                    else:
                        event.part = subevent
                    continue
                elif FORMERLY_ATTRIBUTED_TO.intersects(mods):
                    # the {uncertain_attribution} flag does not apply to this branch, because this branch is not making a statement
                    # about a previous attribution. the uncertainty applies only to the current attribution.
                    assignment = vocab.ObsoleteAssignment(
                        ident=attribute_assignment_id,
                        label=f'Formerly attributed to {artist_label}')
                    event.attributed_by = assignment
                    assignment.assigned_property = 'carried_out_by'
                    assignment.assigned = person
                    continue
                elif UNCERTAIN.intersects(mods):
                    if POSSIBLY.intersects(mods):
                        attrib_assignment_classes.append(
                            vocab.PossibleAssignment)
                        assignment = vocab.make_multitype_obj(
                            *attrib_assignment_classes,
                            ident=attribute_assignment_id,
                            label=f'Possibly attributed to {artist_label}')
                        assignment._label = f'Possibly by {artist_label}'
                    else:
                        attrib_assignment_classes.append(
                            vocab.ProbableAssignment)
                        assignment = vocab.make_multitype_obj(
                            *attrib_assignment_classes,
                            ident=attribute_assignment_id,
                            label=f'Probably attributed to {artist_label}')
                        assignment._label = f'Probably by {artist_label}'
                    event.attributed_by = assignment
                    assignment.assigned_property = 'carried_out_by'
                    assignment.assigned = person
                    continue
                elif COPY_AFTER.intersects(mods):
                    # the {uncertain_attribution} flag does not apply to this branch, because this branch is not making a statement
                    # about the artist of the work, but about the artist of the original work that this work is a copy of.
                    cls = type(hmo)
                    original_id = hmo.id + '-Orig'
                    original_label = f'Original of {hmo_label}'
                    original_hmo = cls(ident=original_id, label=original_label)
                    original_event_id = original_hmo.id + '-Prod'
                    original_event = model.Production(
                        ident=original_event_id,
                        label=f'Production event for {original_label}')
                    original_hmo.produced_by = original_event

                    original_subevent_id = original_event_id + f'-{seq_no}'  # TODO: fix for the case of post-sales merging
                    original_subevent = model.Production(
                        ident=original_subevent_id,
                        label=f'Production sub-event for {artist_label}')
                    original_event.part = original_subevent
                    original_subevent.carried_out_by = person

                    event.influenced_by = original_hmo
                    data['_original_objects'].append(
                        add_crom_data(data={}, what=original_hmo))
                    continue
                elif mods & {'or', 'and'}:
                    pass
                else:
                    print(f'UNHANDLED attrib_mod_auth VALUE: {mods}')
                    pprint.pprint(a)
                    continue

            subprod_path = self.helper.make_uri_path(*a["uri_keys"])
            subevent_id = event_id + f'-{subprod_path}'
            subevent = model.Production(
                ident=subevent_id,
                label=f'Production sub-event for {artist_label}')
            subevent.carried_out_by = person
            if uncertain_attribution or 'or' in mods:
                assignment = vocab.make_multitype_obj(
                    *attrib_assignment_classes,
                    ident=attribute_assignment_id,
                    label=f'Possibly attributed to {artist_label}')
                event.attributed_by = assignment
                assignment.assigned_property = 'part'
                assignment.assigned = subevent
            else:
                event.part = subevent
        data['_artists'] = [a for a in artists if not is_or_anon(a)]
        return data
예제 #7
0
    def model_object_artists(self,
                             data,
                             people,
                             hmo,
                             prod_event,
                             attribution_modifiers,
                             attribution_group_types,
                             attribution_group_names,
                             all_uncertain=False):
        FORMERLY_ATTRIBUTED_TO = attribution_modifiers[
            'formerly attributed to']
        POSSIBLY = attribution_modifiers['possibly by']
        UNCERTAIN = attribution_modifiers['uncertain']
        ATTRIBUTED_TO = attribution_modifiers['attributed to']

        event_uri = prod_event.id
        sales_record = get_crom_object(data['_record'])
        artists = [p for p in people if not self.is_or_anon(p)]
        or_anon_records = any([self.is_or_anon(a) for a in people])
        if or_anon_records:
            all_uncertain = True

        try:
            hmo_label = f'{hmo._label}'
        except AttributeError:
            hmo_label = 'object'

        # 5. Determine if the artist records represent a disjunction (similar to 2 above):
        artist_all_mods = {
            m.lower().strip()
            for a in artists for m in a.get('attrib_mod_auth', '').split(';')
        } - {''}
        all_or_modifiers = ['or' in a['modifiers'] for a in artists]
        artist_group_flag = (not or_anon_records) and len(
            all_or_modifiers) and all(all_or_modifiers)
        artist_group = None
        if artist_group_flag:
            # The artist group URI is just the production event URI with a suffix. When URIs are
            # reconciled during prev/post sale rewriting, this will allow us to also reconcile
            # the URIs for the artist groups (of which there should only be one per production/object)
            group_uri = prod_event.id + '-ArtistGroup'
            g_label = f'Group containing the artist of {hmo_label}'
            artist_group = vocab.UncertainMemberClosedGroup(ident=group_uri,
                                                            label=g_label)
            artist_group.identified_by = model.Name(ident='', content=g_label)
            pi_record_no = data['pi_record_no']
            group_uri_key = ('GROUP', 'PI', pi_record_no, 'ArtistGroup')
            group_data = {
                'uri': group_uri,
                'uri_keys': group_uri_key,
                'role_label': 'uncertain artist'
            }
            add_crom_data(data=group_data, what=artist_group)
            data['_organizations'].append(group_data)

            # 6. Model all the artist records as sub-production events:
            prod_event.carried_out_by = artist_group
            for seq_no, a_data in enumerate(artists):
                mods = a_data['modifiers']
                attribute_assignment_id = self.helper.prepend_uri_key(
                    prod_event.id, f'ASSIGNMENT,Artist-{seq_no}')
                a_data = self.model_person_or_group(data,
                                                    a_data,
                                                    attribution_group_types,
                                                    attribution_group_names,
                                                    seq_no=seq_no,
                                                    role='Artist',
                                                    sales_record=sales_record)
                artist_label = a_data.get(
                    'label')  # TODO: this may not be right for groups
                person = get_crom_object(a_data)
                if ATTRIBUTED_TO.intersects(mods):
                    attrib_assignment_classes = [model.AttributeAssignment]
                    attrib_assignment_classes.append(vocab.PossibleAssignment)
                    assignment = vocab.make_multitype_obj(
                        *attrib_assignment_classes,
                        ident=attribute_assignment_id,
                        label=f'Possibly attributed to {artist_label}')
                    assignment._label = f'Possibly by {artist_label}'
                    person.attributed_by = assignment
                    assignment.assigned_property = 'member_of'
                    assignment.assigned = person
                else:
                    person.member_of = artist_group
        else:
            for seq_no, a_data in enumerate(artists):
                uncertain = all_uncertain
                attribute_assignment_id = self.helper.prepend_uri_key(
                    prod_event.id, f'ASSIGNMENT,Artist-{seq_no}')
                a_data = self.model_person_or_group(data,
                                                    a_data,
                                                    attribution_group_types,
                                                    attribution_group_names,
                                                    seq_no=seq_no,
                                                    role='Artist',
                                                    sales_record=sales_record)
                artist_label = a_data.get(
                    'label')  # TODO: this may not be right for groups
                person = get_crom_object(a_data)
                mods = a_data['modifiers']
                attrib_assignment_classes = [model.AttributeAssignment]
                subprod_path = self.helper.make_uri_path(*a_data["uri_keys"])
                subevent_id = event_uri + f'-{subprod_path}'
                if UNCERTAIN.intersects(mods):
                    if POSSIBLY.intersects(mods):
                        attrib_assignment_classes.append(
                            vocab.PossibleAssignment)
                        assignment = vocab.make_multitype_obj(
                            *attrib_assignment_classes,
                            ident=attribute_assignment_id,
                            label=f'Possibly attributed to {artist_label}')
                        assignment._label = f'Possibly by {artist_label}'
                    else:
                        attrib_assignment_classes.append(
                            vocab.ProbableAssignment)
                        assignment = vocab.make_multitype_obj(
                            *attrib_assignment_classes,
                            ident=attribute_assignment_id,
                            label=f'Probably attributed to {artist_label}')
                        assignment._label = f'Probably by {artist_label}'

                    # TODO: this assigns an uncertain carried_out_by property directly to the top-level production;
                    #       should it instead be an uncertain sub-production part?
                    prod_event.attributed_by = assignment
                    assignment.assigned_property = 'carried_out_by'
                    assignment.assigned = person
                elif FORMERLY_ATTRIBUTED_TO.intersects(mods):
                    attrib_assignment_classes = [vocab.ObsoleteAssignment]
                    if uncertain:
                        attrib_assignment_classes.append(
                            vocab.PossibleAssignment)
                    assignment = vocab.make_multitype_obj(
                        *attrib_assignment_classes,
                        ident=attribute_assignment_id,
                        label=f'Formerly attributed to {artist_label}')
                    prod_event.attributed_by = assignment
                    assignment.assigned_property = 'carried_out_by'
                    assignment.assigned = person
                else:
                    if uncertain or ATTRIBUTED_TO.intersects(mods):
                        attrib_assignment_classes.append(
                            vocab.PossibleAssignment)
                        assignment = vocab.make_multitype_obj(
                            *attrib_assignment_classes,
                            ident=attribute_assignment_id,
                            label=f'Possibly attributed to {artist_label}')
                        prod_event.attributed_by = assignment
                        assignment.assigned_property = 'carried_out_by'
                        assignment.assigned = person
                    else:
                        subevent = model.Production(
                            ident=subevent_id,
                            label=f'Production sub-event for {artist_label}')
                        subevent.carried_out_by = person
                        prod_event.part = subevent
예제 #8
0
    def model_object_influence(self,
                               data,
                               people,
                               hmo,
                               prod_event,
                               attribution_modifiers,
                               attribution_group_types,
                               attribution_group_names,
                               all_uncertain=False):
        STYLE_OF = attribution_modifiers['style of']
        COPY_AFTER = attribution_modifiers['copy after']
        NON_ARTIST_MODS = COPY_AFTER | STYLE_OF
        GROUP_TYPES = set(attribution_group_types.values())
        GROUP_MODS = {
            k
            for k, v in attribution_group_types.items() if v in GROUP_TYPES
        }

        non_artist_assertions = people
        sales_record = get_crom_object(data['_record'])

        try:
            hmo_label = f'{hmo._label}'
        except AttributeError:
            hmo_label = 'object'

        # 2. Determine if the non-artist records represent a disjunction. If all such records have an "or" modifier, we will represent all the people as a Group, and classify it to indicate that one and only one of the named people was the actor. If there is at least one 'or' modifier, but not all of the records have 'or', then we model each such record with uncertainty.
        non_artist_all_mods = {
            m.lower().strip()
            for a in non_artist_assertions
            for m in a.get('attrib_mod_auth', '').split(';')
        } - {''}
        non_artist_group_flag = len(non_artist_assertions) and all(
            ['or' in a['modifiers'] for a in non_artist_assertions])
        non_artist_group = None
        if non_artist_group_flag:
            non_artist_mod = list(
                NON_ARTIST_MODS.intersection(non_artist_all_mods))[0]
            # The artist group URI is just the production event URI with a suffix. When URIs are
            # reconciled during prev/post sale rewriting, this will allow us to also reconcile
            # the URIs for the artist groups (of which there should only be one per production/object)
            group_uri = prod_event.id + '-NonArtistGroup'
            g_label = f'Group containing the {non_artist_mod} of {hmo_label}'
            non_artist_group = vocab.UncertainMemberClosedGroup(
                ident=group_uri, label=g_label)
            non_artist_group.identified_by = model.Name(ident='',
                                                        content=g_label)
            group_data = {
                'uri': group_uri,
                'role_label': 'uncertain influencer'
            }
            make_la_org = pipeline.linkedart.MakeLinkedArtOrganization()
            group_data = make_la_org(group_data)
            data['_organizations'].append(group_data)

        # 3. Model all the non-artist records as an appropriate property/relationship of the object or production event:
        for seq_no, a_data in enumerate(non_artist_assertions):
            a_data = self.model_person_or_group(data,
                                                a_data,
                                                attribution_group_types,
                                                attribution_group_names,
                                                seq_no=seq_no,
                                                role='NonArtist',
                                                sales_record=sales_record)
            artist_label = a_data.get('label')
            person = get_crom_object(a_data)

            mods = a_data['modifiers']
            attrib_assignment_classes = [model.AttributeAssignment]
            uncertain = all_uncertain
            if uncertain or 'or' in mods:
                if non_artist_group_flag:
                    person.member_of = non_artist_group
                else:
                    uncertain = True
                    attrib_assignment_classes.append(vocab.PossibleAssignment)

            if STYLE_OF.intersects(mods):
                attribute_assignment_id = self.helper.prepend_uri_key(
                    prod_event.id, f'ASSIGNMENT,NonArtist-{seq_no}')
                assignment = vocab.make_multitype_obj(
                    *attrib_assignment_classes,
                    ident=attribute_assignment_id,
                    label=f'In the style of {artist_label}')
                prod_event.attributed_by = assignment
                assignment.assigned_property = 'influenced_by'
                assignment.property_classified_as = vocab.instances['style of']
                assignment.assigned = person
            elif COPY_AFTER.intersects(mods):
                cls = type(hmo)
                # The original object 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 original object (of which there should be at most one per object)
                original_id = hmo.id + '-Original'
                original_label = f'Original of {hmo_label}'
                original_hmo = cls(ident=original_id, label=original_label)

                # original title
                original_hmo.identified_by = vocab.ConstructedTitle(
                    ident='', content=f'[Work] by {artist_label}')

                # Similarly for the production of the original object.
                original_event_id = original_hmo.id + '-Production'
                original_event = model.Production(
                    ident=original_event_id,
                    label=f'Production event for {original_label}')
                original_hmo.produced_by = original_event

                original_subevent_id = original_event_id + f'-{seq_no}'  # TODO: fix for the case of post-sales merging
                original_subevent = model.Production(
                    ident=original_subevent_id,
                    label=f'Production sub-event for {artist_label}')
                original_event.part = original_subevent
                original_subevent.carried_out_by = person

                if uncertain:
                    assignment = vocab.make_multitype_obj(
                        *attrib_assignment_classes,
                        ident=attribute_assignment_id,
                        label=f'Possibly influenced by {person._label}')
                    prod_event.attributed_by = assignment
                    assignment.assigned_property = 'influenced_by'
                    assignment.assigned = original_hmo
                else:
                    prod_event.influenced_by = original_hmo
                data['_original_objects'].append(
                    add_crom_data(data={'uri': original_id},
                                  what=original_hmo))
            else:
                warnings.warn(
                    f'Unrecognized non-artist attribution modifers: {mods}')
예제 #9
0
    def add_names(self,
                  data: dict,
                  referrer=None,
                  role=None,
                  group=False,
                  **kwargs):
        '''
		Based on the presence of `auth_name` and/or `name` fields in `data`, sets the
		`label`, `names`, and `identifier` keys to appropriate strings/`model.Identifier`
		values.

		If the `role` string is given (e.g. 'artist'), also sets the `role_label` key
		to a value (e.g. 'artist “RUBENS, PETER PAUL”').
		'''
        data.setdefault('identifiers', [])
        auth_name = data.get('auth_name', '')
        disp_name = data.get('auth_display_name')
        name_types = [vocab.PrimaryName]

        personalNameType = vocab.CorporateName if group else vocab.PersonalName

        if disp_name:
            if auth_name:
                data['identifiers'].append(
                    vocab.PrimaryName(ident='', content=auth_name))
                data['label'] = auth_name
            auth_name = disp_name
            name_types = [personalNameType, vocab.DisplayName]

        role_label = None
        if self.acceptable_person_auth_name(auth_name):
            if role:
                role_label = f'{role} “{auth_name}”'
            data.setdefault('label', auth_name)
            pname = vocab.make_multitype_obj(
                *name_types, ident='', content=auth_name
            )  # NOTE: most of these are also vocab.SortName, but not 100%, so witholding that assertion for now
            if referrer:
                pname.referred_to_by = referrer
            data['identifiers'].append(pname)

        data.setdefault('names', [])

        names = []
        name = data.get('name')
        if name:
            del data[
                'name']  # this will be captured in the 'names' array, so remove it here so the output isn't duplicated
            names.append(name)
        variant_names = data.get('variant_names')
        if variant_names:
            names += [n.strip() for n in variant_names.split(';')]

        for name in names:
            if role and not role_label:
                role_label = f'{role} “{name}”'
            name_kwargs = {}
            # 			name_kwargs['classified_as'] = model.Type(ident='http://vocab.getty.edu/aat/300266386', label='Personal Name')
            name_kwargs['classified_as'] = personalNameType
            if referrer:
                name_kwargs['referred_to_by'] = [referrer]
            data['names'].append((name, name_kwargs))
            data.setdefault('label', name)
        data.setdefault('label', '(Anonymous)')

        if role and not role_label:
            role_label = f'anonymous {role}'

        if role:
            data['role_label'] = role_label
예제 #10
0
    def add_props(self, data: dict, role=None, **kwargs):
        role = role if role else 'person'
        auth_name = data.get('auth_name', '')
        period_match = self.anon_period_re.match(auth_name)
        nationalities = []
        if 'nationality' in data:
            nationality = data['nationality']
            if isinstance(nationality, str):
                nationalities += [
                    n.lower().strip() for n in nationality.split(';')
                ]
            elif isinstance(nationality, list):
                nationalities += [n.lower() for n in nationality]

        data['nationality'] = []
        data.setdefault('referred_to_by', [])

        # 		name = data['label']
        # 		active = self.clamped_timespan_args(data, name)
        # 		cb = data.get('corporate_body')
        # 		if active:
        # 			pact_uri = data['uri'] + '-ProfAct-active'
        # 			a = self.professional_activity(name, ident=pact_uri, **active)
        # 			data['events'].append(a)

        notes_field_classification = {
            'brief_notes': (vocab.BiographyStatement, vocab.External),
            'text': (vocab.BiographyStatement, vocab.Internal),
            'internal_notes': (vocab.BiographyStatement, vocab.Internal),
            'working_notes': (vocab.ResearchStatement, vocab.Internal),
        }
        for key, note_classification in notes_field_classification.items():
            if key in data:
                for content in [n.strip() for n in data[key].split(';')]:
                    cite = vocab.make_multitype_obj(*note_classification,
                                                    ident='',
                                                    content=content)
                    data['referred_to_by'].append(cite)

        for key in ('name_cite', 'bibliography'):
            if data.get(key):
                cite = vocab.BibliographyStatement(ident='', content=data[key])
                data['referred_to_by'].append(cite)

        if data.get('name_cite'):
            cite = vocab.BibliographyStatement(ident='',
                                               content=data['name_cite'])
            data['referred_to_by'].append(cite)

        if self.is_anonymous_group(auth_name):
            nationality_match = self.anon_nationality_re.match(auth_name)
            dated_nationality_match = self.anon_dated_nationality_re.match(
                auth_name)
            dated_match = self.anon_dated_re.match(auth_name)
            data.setdefault('events', [])
            if nationality_match:
                with suppress(ValueError):
                    nationality = nationality_match.group(1).lower()
                    nationalities.append(nationality)
                    group_label = self.anonymous_group_label(
                        role, nationality=nationality)
                    data['label'] = group_label
            elif dated_nationality_match:
                with suppress(ValueError):
                    nationality = dated_nationality_match.group(1).lower()
                    nationalities.append(nationality)
                    century = int(dated_nationality_match.group(2))
                    group_label = self.anonymous_group_label(
                        role, century=century, nationality=nationality)
                    data['label'] = group_label
                    pact_uri = data['uri'] + '-ProfAct-dated-natl'
                    a = self.professional_activity(
                        group_label,
                        classified_as=[vocab.ActiveOccupation],
                        ident=pact_uri,
                        century=century,
                        narrow=True)
                    data['events'].append(a)
            elif dated_match:
                with suppress(ValueError):
                    century = int(dated_match.group(1))
                    group_label = self.anonymous_group_label(role,
                                                             century=century)
                    data['label'] = group_label
                    pact_uri = data['uri'] + '-ProfAct-dated'
                    a = self.professional_activity(
                        group_label,
                        classified_as=[vocab.ActiveOccupation],
                        ident=pact_uri,
                        century=century,
                        narrow=True)
                    data['events'].append(a)
            elif period_match:
                period = period_match.group(1).lower()
                data['label'] = f'anonymous {period} {role}s'
        for nationality in nationalities:
            key = f'{nationality.lower()} nationality'
            n = vocab.instances.get(key)
            if n:
                data['nationality'].append(n)
            else:
                warnings.warn(
                    f'No nationality instance found in crom for: {key!r}')