Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Accessing settings of REST endpoints from other modules #245

Open
mesemus opened this issue Feb 20, 2019 · 0 comments
Open

Accessing settings of REST endpoints from other modules #245

mesemus opened this issue Feb 20, 2019 · 0 comments

Comments

@mesemus
Copy link

mesemus commented Feb 20, 2019

Hello folks,

Intro:
I'm in the middle of implementing our institutional repository on top of invenio 3. For now I have two record types: Thesis (metadata about student thesis) and Attachment (for example fulltext, defence transcript, ... Each attachment has associated ACLs and potentially multiple files, such as original pdf and converted pdf/a). Thesis and n attachments are referenced via thesis id and for a couple of reasons I need to keep the two data types and not denormalize/merge them into one.

So far I've created two helper modules: acls providing generic mechanism for evaluating ACLs directly within elasticsearch queries and links defining LinkedObjectSerializerMixin(PreprocessorMixin) that in generic manner adds to thesis representation its associated attachments' metadata.

Problem:
What I'm facing is that I need to reference settings of REST endpoints - for example, when Attachments are searched for inside the mixin I would like to use the appropriate RecordsSearch - the same that is used for accessing Attachment through REST. So far I've ended up with code bloated with obj_or_import_string:

rest_configuration = current_app.config['RECORDS_REST_ENDPOINTS'][self.other_side_rest_endpoint]
search = obj_or_import_string(rest_configuration.get('search_class', None), default=RecordsSearch)

Suggestion:

What about adding a dictionary current_records_rest.endpoints that would contain the configuration of endpoints that would be already resolved via the obj_or_import_string code that is now present at the beginning of create_url_rules ?

read_permission_factory = obj_or_import_string(
read_permission_factory_imp
)
create_permission_factory = obj_or_import_string(
create_permission_factory_imp
)
update_permission_factory = obj_or_import_string(
update_permission_factory_imp
)
delete_permission_factory = obj_or_import_string(
delete_permission_factory_imp
)
list_permission_factory = obj_or_import_string(
list_permission_factory_imp
)
links_factory = obj_or_import_string(
links_factory_imp, default=default_links_factory
)
# For backward compatibility. Previous signature was links_factory(pid).
if wrap_links_factory(links_factory):
orig_links_factory = links_factory
def links_factory(pid, record=None, **kwargs):
return orig_links_factory(pid)
record_class = obj_or_import_string(
record_class, default=Record
)
search_class = obj_or_import_string(
search_class, default=RecordsSearch
)
indexer_class = obj_or_import_string(
indexer_class, default=None
)
search_class_kwargs = {}
if search_index:
search_class_kwargs['index'] = search_index
else:
search_index = search_class.Meta.index
if search_type:
search_class_kwargs['doc_type'] = search_type
else:
search_type = search_class.Meta.doc_types
if search_class_kwargs:
search_class = partial(search_class, **search_class_kwargs)
if record_loaders:
record_loaders = {mime: obj_or_import_string(func)
for mime, func in record_loaders.items()}
record_serializers = {mime: obj_or_import_string(func)
for mime, func in record_serializers.items()}
search_serializers = {mime: obj_or_import_string(func)
for mime, func in search_serializers.items()}
resolver = Resolver(pid_type=pid_type, object_type='rec',
getter=partial(record_class.get_record,
with_deleted=True))

Then my module would just call

current_records_rest.endpoints[self.other_side_rest_endpoint].search_class 
or 
current_records_rest.endpoints[self.other_side_rest_endpoint]['search_class']

and would get the actual implementation of RecordsSearch.

If it makes sense I'm willing to create a pull request. Your opinions?

Thanks for all the work, so far I'm really happy with the ease of implementation and repository speed,

Mirek

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

1 participant