SourceDescObservationServiceImpl.java
/*
* Copyright 2021 Global Crop Diversity Trust
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package org.gringlobal.service.impl;
import java.util.List;
import java.util.Objects;
import java.util.stream.Collectors;
import lombok.extern.slf4j.Slf4j;
import org.gringlobal.api.exception.InvalidApiUsageException;
import org.gringlobal.custom.elasticsearch.SearchException;
import org.gringlobal.model.SourceDescObservation;
import org.gringlobal.model.SourceDescriptor;
import org.gringlobal.model.SourceDescriptorCode;
import org.gringlobal.persistence.AccessionSourceRepository;
import org.gringlobal.persistence.SourceDescObservationRepository;
import org.gringlobal.service.SourceDescObservationService;
import org.gringlobal.service.SourceDescriptorCodeService;
import org.gringlobal.service.SourceDescriptorCodeTranslationService.TranslatedSourceDescriptorCode;
import org.gringlobal.service.SourceDescriptorService;
import org.gringlobal.service.SourceDescriptorTranslationService.TranslatedSourceDescriptor;
import org.gringlobal.service.filter.SourceDescObservationFilter;
import org.gringlobal.service.filter.SourceDescriptorCodeFilter;
import org.gringlobal.service.filter.SourceDescriptorFilter;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.domain.Page;
import org.springframework.data.domain.PageRequest;
import org.springframework.data.domain.Pageable;
import org.springframework.security.access.prepost.PostAuthorize;
import org.springframework.security.access.prepost.PreAuthorize;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;
@Service
@Transactional(readOnly = true)
@Slf4j
public class SourceDescObservationServiceImpl extends FilteredCRUDService2Impl<SourceDescObservation, SourceDescObservationFilter, SourceDescObservationRepository>
implements SourceDescObservationService {
@Autowired
private SourceDescriptorService sourceDescriptorService;
@Autowired
private SourceDescriptorCodeService sourceDescriptorCodeService;
@Autowired
private AccessionSourceRepository accessionSourceRepository;
@Override
@Transactional
@PostAuthorize("@ggceSec.actionAllowed('PassportData', 'WRITE', returnObject.accessionSource.accession.site)")
public SourceDescObservation create(SourceDescObservation source) {
source.setSourceDescriptor(sourceDescriptorService.get(source.getSourceDescriptor().getId()));
if (source.getSourceDescriptorCode() != null) {
source.setSourceDescriptorCode(sourceDescriptorCodeService.get(source.getSourceDescriptorCode().getId()));
}
SourceDescObservation target = new SourceDescObservation();
target.apply(source);
SourceDescObservation saved = repository.save(target);
saved.lazyLoad();
var accessionSource = accessionSourceRepository.getReferenceById(saved.getAccessionSource().getId());
accessionSource.getAccession().lazyLoad();
saved.setAccessionSource(accessionSource);
return saved;
}
@Override
@Transactional
@PreAuthorize("@ggceSec.actionAllowed('PassportData', 'WRITE', #target.accessionSource.accession.site)")
public SourceDescObservation update(SourceDescObservation updated, SourceDescObservation target) {
if (updated == null) {
throw new InvalidApiUsageException("SourceDescObservation must be provided.");
}
updated.setSourceDescriptor(sourceDescriptorService.get(updated.getSourceDescriptor().getId()));
if (updated.getSourceDescriptorCode() != null) {
updated.setSourceDescriptorCode(sourceDescriptorCodeService.get(updated.getSourceDescriptorCode().getId()));
}
log.debug("Update SourceDescObservation. Input data {}", updated);
target.apply(updated);
SourceDescObservation saved = repository.save(target);
return _lazyLoad(saved);
}
@Override
@Transactional
@PreAuthorize("@ggceSec.actionAllowed('PassportData', 'WRITE', #target.accessionSource.accession.site)")
public SourceDescObservation updateFast(SourceDescObservation updated, SourceDescObservation target) {
target.apply(updated);
return repository.save(target);
}
@Override
@Transactional(readOnly = true)
public Page<SourceDescObservation> list(Class<SourceDescObservation> clazz, SourceDescObservationFilter filter, Pageable page, String... boostFields) throws SearchException {
Page<SourceDescObservation> sourceDescObservations = super.list(clazz, filter, page, boostFields);
sourceDescObservations.getContent().forEach(SourceDescObservation::lazyLoad);
return sourceDescObservations;
}
@Override
public TranslatedSourceDescObservation getTranslated(long id) {
SourceDescObservation loadedObservation = super.load(id);
TranslatedSourceDescObservation translated = new TranslatedSourceDescObservation();
translated.observation = loadedObservation;
SourceDescriptor loadedSourceDescriptor = loadedObservation.getSourceDescriptor();
if (loadedSourceDescriptor != null) {
translated.translatedSourceDescriptor = sourceDescriptorService.loadTranslated(loadedSourceDescriptor.getId());
}
SourceDescriptorCode loadedSourceDescriptorCode = loadedObservation.getSourceDescriptorCode();
if (loadedSourceDescriptorCode != null) {
translated.translatedSourceDescriptorCode = sourceDescriptorCodeService.loadTranslated(loadedSourceDescriptorCode.getId());
}
return translated;
}
@Override
@Transactional(readOnly = true)
public Page<TranslatedSourceDescObservation> listTranslated(SourceDescObservationFilter filter, Pageable page) throws SearchException {
Page<SourceDescObservation> loadedSourceDescObservationPage = super.list(filter, page);
// fetch translated source descriptors by ids from observations
SourceDescriptorFilter sourceDescriptorFilter = new SourceDescriptorFilter();
sourceDescriptorFilter.id = loadedSourceDescObservationPage.stream()
.map(SourceDescObservation::getSourceDescriptor)
.map(SourceDescriptor::getId)
.collect(Collectors.toSet());
List<TranslatedSourceDescriptor> translatedSourceDescriptors = sourceDescriptorService.listFiltered(sourceDescriptorFilter, PageRequest.of(0, loadedSourceDescObservationPage.getSize())).getContent();
// fetch translated source descriptor codes by ids from observations
SourceDescriptorCodeFilter sourceDescriptorCodeFilter = new SourceDescriptorCodeFilter();
sourceDescriptorCodeFilter.id = loadedSourceDescObservationPage.stream()
.map(SourceDescObservation::getSourceDescriptorCode)
.filter(Objects::nonNull)
.map(SourceDescriptorCode::getId)
.collect(Collectors.toSet());
List<TranslatedSourceDescriptorCode> translatedSourceDescriptorCodes = sourceDescriptorCodeService.listFiltered(sourceDescriptorCodeFilter, PageRequest.of(0, loadedSourceDescObservationPage.getSize())).getContent();
Page<TranslatedSourceDescObservation> translatedSourceDescObservations = loadedSourceDescObservationPage.map(observation -> covert(observation, translatedSourceDescriptors, translatedSourceDescriptorCodes));
return translatedSourceDescObservations;
}
private TranslatedSourceDescObservation covert(SourceDescObservation observation, List<TranslatedSourceDescriptor> translatedDescriptors, List<TranslatedSourceDescriptorCode> translatedCodes) {
TranslatedSourceDescObservation translatedObservation = new TranslatedSourceDescObservation();
translatedObservation.observation = observation;
var translatedDescriptor = translatedDescriptors.stream()
.filter(translatedSourceDescriptor -> Objects.equals(translatedSourceDescriptor.entity.getId(), observation.getSourceDescriptor().getId()))
.findFirst().orElse(null);
translatedObservation.translatedSourceDescriptor = translatedDescriptor;
if (Objects.nonNull(observation.getSourceDescriptorCode())) {
translatedObservation.translatedSourceDescriptorCode = translatedCodes.stream()
.filter(translatedCode -> Objects.equals(translatedCode.entity.getId(), observation.getSourceDescriptorCode().getId()))
.findFirst().orElse(null);
}
return translatedObservation;
}
}