Skip to content

Commit

Permalink
[kbss-cvut/record-manager-ui#38] Set imported record phase to open un…
Browse files Browse the repository at this point in the history
…less specified otherwise.

When current user is admin, imported record phase is preserved.
  • Loading branch information
ledsoft committed Dec 22, 2023
1 parent dce1d6d commit 69da5c1
Show file tree
Hide file tree
Showing 3 changed files with 44 additions and 40 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -64,7 +64,8 @@ public interface PatientRecordService extends BaseService<PatientRecord> {
* records.
* <p>
* If the current user is an admin, the import procedure retains provenance data of the record. Otherwise, the
* current user is set as the record's author.
* current user is set as the record's author. Also, if the current user is not an admin, the phase of all
* the imported records is set to {@link RecordPhase#open}, for admin, the phase of the records is retained.
*
* @param records Records to import
* @return Instance representing the import result
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -22,6 +22,7 @@
import java.util.Date;
import java.util.List;
import java.util.Objects;
import java.util.Optional;

@Service
public class RepositoryPatientRecordService extends KeySupportingRepositoryService<PatientRecord>
Expand Down Expand Up @@ -92,11 +93,15 @@ protected void preUpdate(PatientRecord instance) {
public RecordImportResult importRecords(List<PatientRecord> records) {
Objects.requireNonNull(records);
LOG.debug("Importing records.");
return importRecordsImpl(records, Optional.empty());
}

private RecordImportResult importRecordsImpl(List<PatientRecord> records, Optional<RecordPhase> targetPhase) {
final User author = securityUtils.getCurrentUser();
final Date created = new Date();
final RecordImportResult result = new RecordImportResult(records.size());
records.forEach(r -> {
setImportedRecordProvenance(author, created, r);
setImportedRecordProvenance(author, created, targetPhase, r);
if (recordDao.exists(r.getUri())) {
LOG.warn("Record {} already exists. Skipping it.", Utils.uriToString(r.getUri()));
result.addError("Record " + Utils.uriToString(r.getUri()) + " already exists.");
Expand All @@ -108,13 +113,18 @@ public RecordImportResult importRecords(List<PatientRecord> records) {
return result;
}

private void setImportedRecordProvenance(User currentUser, Date now, PatientRecord record) {
private void setImportedRecordProvenance(User currentUser, Date now, Optional<RecordPhase> targetPhase,
PatientRecord record) {
if (!currentUser.isAdmin()) {
record.setAuthor(currentUser);
record.setInstitution(currentUser.getInstitution());
record.setDateCreated(now);
} else if (!userService.exists(record.getAuthor().getUri())) {
throw new RecordAuthorNotFoundException("Author of record " + record + "not found during import.");
targetPhase.ifPresentOrElse(record::setPhase, () -> record.setPhase(RecordPhase.open));
} else {
targetPhase.ifPresent(record::setPhase);
if (!userService.exists(record.getAuthor().getUri())) {
throw new RecordAuthorNotFoundException("Author of record " + record + "not found during import.");
}
}
}

Expand All @@ -124,7 +134,6 @@ private void setImportedRecordProvenance(User currentUser, Date now, PatientReco
public RecordImportResult importRecords(List<PatientRecord> records, RecordPhase targetPhase) {
Objects.requireNonNull(records);
LOG.debug("Importing records to target phase '{}'.", targetPhase);
records.forEach(r -> r.setPhase(targetPhase));
return importRecords(records);
return importRecordsImpl(records, Optional.ofNullable(targetPhase));
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -20,6 +20,7 @@
import org.mockito.Mock;
import org.mockito.junit.jupiter.MockitoExtension;

import java.net.URI;
import java.util.Date;
import java.util.List;

Expand Down Expand Up @@ -62,13 +63,7 @@ void setUp() {
@Test
void importRecordsSetsCurrentUserAsAuthorWhenTheyAreRegularUserAndImportsSpecifiedRecords() {
final User originalAuthor = Generator.generateUser(Generator.generateInstitution());
final List<PatientRecord> toImport =
List.of(Generator.generatePatientRecord(originalAuthor), Generator.generatePatientRecord(originalAuthor));
toImport.forEach(r -> {
// Simulate that the records existed in another deployment from which they are imported
r.setKey(IdentificationUtils.generateKey());
r.setDateCreated(new Date(System.currentTimeMillis() - 10000L));
});
final List<PatientRecord> toImport = generateRecordsToImport(originalAuthor);
when(recordDao.exists(any())).thenReturn(false);

final RecordImportResult result = sut.importRecords(toImport);
Expand All @@ -87,16 +82,21 @@ void importRecordsSetsCurrentUserAsAuthorWhenTheyAreRegularUserAndImportsSpecifi
}
}

@Test
void importRecordsRetainsRecordProvenanceDataWhenCurrentUserIsAdmin() {
final User originalAuthor = Generator.generateUser(Generator.generateInstitution());
private List<PatientRecord> generateRecordsToImport(User originalAuthor) {
final List<PatientRecord> toImport =
List.of(Generator.generatePatientRecord(originalAuthor), Generator.generatePatientRecord(originalAuthor));
toImport.forEach(r -> {
// Simulate that the records existed in another deployment from which they are imported
r.setKey(IdentificationUtils.generateKey());
r.setDateCreated(new Date(System.currentTimeMillis() - 10000L));
});
return toImport;
}

@Test
void importRecordsRetainsRecordProvenanceDataWhenCurrentUserIsAdmin() {
final User originalAuthor = Generator.generateUser(Generator.generateInstitution());
final List<PatientRecord> toImport = generateRecordsToImport(originalAuthor);
user.addType(Vocabulary.s_c_administrator);
Environment.setCurrentUser(user);
when(userService.exists(originalAuthor.getUri())).thenReturn(true);
Expand All @@ -112,19 +112,14 @@ void importRecordsRetainsRecordProvenanceDataWhenCurrentUserIsAdmin() {
assertEquals(toImport.get(i).getKey(), imported.get(i).getKey());
assertEquals(originalAuthor, imported.get(i).getAuthor());
assertEquals(toImport.get(i).getDateCreated(), imported.get(i).getDateCreated());
assertEquals(toImport.get(i).getPhase(), imported.get(i).getPhase());
}
}

@Test
void importRecordsThrowsRecordAuthorNotFoundExceptionWhenAdminImportsRecordsAndRecordAuthorIsNotFound() {
final User originalAuthor = Generator.generateUser(Generator.generateInstitution());
final List<PatientRecord> toImport =
List.of(Generator.generatePatientRecord(originalAuthor), Generator.generatePatientRecord(originalAuthor));
toImport.forEach(r -> {
// Simulate that the records existed in another deployment from which they are imported
r.setKey(IdentificationUtils.generateKey());
r.setDateCreated(new Date(System.currentTimeMillis() - 10000L));
});
final List<PatientRecord> toImport = generateRecordsToImport(originalAuthor);
user.addType(Vocabulary.s_c_administrator);
Environment.setCurrentUser(user);

Expand All @@ -133,17 +128,11 @@ void importRecordsThrowsRecordAuthorNotFoundExceptionWhenAdminImportsRecordsAndR

@Test
void importRecordsSkipsImportingRecordsThatAlreadyExist() {
final List<PatientRecord> toImport =
List.of(Generator.generatePatientRecord(user), Generator.generatePatientRecord(user));
final User originalAuthor = Generator.generateUser(Generator.generateInstitution());
final List<PatientRecord> toImport = generateRecordsToImport(originalAuthor);
final PatientRecord existing = toImport.get(Generator.randomIndex(toImport));
when(recordDao.exists(any(URI.class))).thenReturn(false);
when(recordDao.exists(existing.getUri())).thenReturn(true);
toImport.forEach(r -> {
// Simulate that the records existed in another deployment from which they are imported
r.setKey(IdentificationUtils.generateKey());
r.setDateCreated(new Date(System.currentTimeMillis() - 10000L));
r.setAuthor(originalAuthor);
});

final RecordImportResult result = sut.importRecords(toImport);
assertEquals(toImport.size(), result.getTotalCount());
Expand All @@ -154,21 +143,26 @@ void importRecordsSkipsImportingRecordsThatAlreadyExist() {

@Test
void importRecordsWithPhaseSetsSpecifiedPhaseToAllRecords() {
final List<PatientRecord> toImport =
List.of(Generator.generatePatientRecord(user), Generator.generatePatientRecord(user));
final User originalAuthor = Generator.generateUser(Generator.generateInstitution());
final List<PatientRecord> toImport = generateRecordsToImport(originalAuthor);
final RecordPhase targetPhase = RecordPhase.values()[Generator.randomInt(0, RecordPhase.values().length)];
toImport.forEach(r -> {
// Simulate that the records existed in another deployment from which they are imported
r.setKey(IdentificationUtils.generateKey());
r.setDateCreated(new Date(System.currentTimeMillis() - 10000L));
r.setAuthor(originalAuthor);
});
when(recordDao.exists(any())).thenReturn(false);

sut.importRecords(toImport, targetPhase);
final ArgumentCaptor<PatientRecord> captor = ArgumentCaptor.forClass(PatientRecord.class);
verify(recordDao, times(toImport.size())).persist(captor.capture());
captor.getAllValues().forEach(r -> assertEquals(targetPhase, r.getPhase()));
}

@Test
void importRecordsSetsRecordPhaseToOpenOnAllImportedRecordsWhenCurrentUserIsRegularUser() {
final User originalAuthor = Generator.generateUser(Generator.generateInstitution());
final List<PatientRecord> toImport = generateRecordsToImport(originalAuthor);
when(recordDao.exists(any())).thenReturn(false);

sut.importRecords(toImport);
final ArgumentCaptor<PatientRecord> captor = ArgumentCaptor.forClass(PatientRecord.class);
verify(recordDao, times(toImport.size())).persist(captor.capture());
captor.getAllValues().forEach(r -> assertEquals(RecordPhase.open, r.getPhase()));
}
}

0 comments on commit 69da5c1

Please sign in to comment.