Skip to content

Commit

Permalink
Merge pull request #232 from medizininformatik-initiative/release/v4.1.0
Browse files Browse the repository at this point in the history
Release/v4.1.0
  • Loading branch information
juliangruendner authored Nov 9, 2023
2 parents 06d6319 + 26943d0 commit 0114da9
Show file tree
Hide file tree
Showing 29 changed files with 1,361 additions and 131 deletions.
26 changes: 26 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,32 @@ All notable changes to this project will be documented in this file.

The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/),

## [UNRELEASED] - yyyy-mm-dd

### Added
### Changed
### Deprecated
### Removed
### Fixed
### Security

The full changelog can be found [here](https://todo).

## [4.1.0] - 2023-11-09

### Added
- Make order of main categories configurable ([#219](https://github.com/medizininformatik-initiative/feasibility-backend/issues/219))
- Save and load query results for saved queries ([#199](https://github.com/medizininformatik-initiative/feasibility-backend/issues/199))
- Support CRUD for query templates ([#214](https://github.com/medizininformatik-initiative/feasibility-backend/issues/214))

### Fixed
- Fix code scanning alert - parser confusion leads to OOM ([#221](https://github.com/medizininformatik-initiative/feasibility-backend/issues/221))
- Fix code scanning alert - Missing Override annotation ([#223](https://github.com/medizininformatik-initiative/feasibility-backend/issues/223))
- Fix code scanning alert - Unread local variable ([#222](https://github.com/medizininformatik-initiative/feasibility-backend/issues/222))

### Security
- Update Spring Boot to 3.1.5 ([#227](https://github.com/medizininformatik-initiative/feasibility-backend/issues/227))

## [4.0.0] - 2023-10-06

### Added
Expand Down
65 changes: 33 additions & 32 deletions README.md

Large diffs are not rendered by default.

1 change: 1 addition & 0 deletions docker-compose.yml
Original file line number Diff line number Diff line change
Expand Up @@ -35,6 +35,7 @@ services:
API_BASE_URL: ${CODEX_FEASIBILITY_BACKEND_API_BASE_URL:-}
QUERY_VALIDATION_ENABLED: ${CODEX_FEASIBILITY_BACKEND_QUERY_VALIDATION_ENABLED:-true}
QUERYRESULT_EXPIRY_MINUTES: ${CODEX_FEASIBILITY_BACKEND_QUERYRESULT_EXPIRY_MINUTES:-5}
MAX_SAVED_QUERIES_PER_USER: ${CODEX_FEASIBILITY_BACKEND_MAX_SAVED_QUERIES_PER_USER:-10}
# ---- Direct
BROKER_CLIENT_DIRECT_USE_CQL: ${CODEX_FEASIBILITY_BACKEND_BROKER_CLIENT_DIRECT_USE_CQL:-false}
BROKER_CLIENT_OBFUSCATE_RESULT_COUNT: ${CODEX_FEASIBILITY_BACKEND_BROKER_CLIENT_OBFUSCATE_RESULT_COUNT:-false}
Expand Down
10 changes: 5 additions & 5 deletions pom.xml
Original file line number Diff line number Diff line change
Expand Up @@ -5,13 +5,13 @@
<parent>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-parent</artifactId>
<version>3.1.3</version>
<version>3.1.5</version>
<relativePath /> <!-- lookup parent from repository -->
</parent>

<groupId>de.medizininformatik-initiative</groupId>
<artifactId>FeasibilityGuiBackend</artifactId>
<version>4.0.0</version>
<version>4.1.0</version>

<name>FeasibilityGuiBackend</name>
<description>Backend of the Feasibility GUI</description>
Expand All @@ -26,7 +26,7 @@
<java.version>17</java.version>
<mockwebserver.version>4.10.0</mockwebserver.version>
<okhttp3.version>4.10.0</okhttp3.version>
<ontology-tag>v2.1.13-RC</ontology-tag>
<ontology-tag>v2.1.24</ontology-tag>
</properties>

<dependencies>
Expand Down Expand Up @@ -124,7 +124,7 @@
<dependency>
<groupId>org.json</groupId>
<artifactId>json</artifactId>
<version>20230227</version>
<version>20231013</version>
</dependency>

<dependency>
Expand Down Expand Up @@ -198,7 +198,7 @@
<dependency>
<groupId>de.medizininformatik-initiative</groupId>
<artifactId>sq2cql</artifactId>
<version>0.2.0-alpha.1</version>
<version>0.2.0</version>
</dependency>

<dependency>
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -21,10 +21,11 @@
import org.springframework.transaction.annotation.Transactional;
import reactor.core.publisher.Mono;

import java.sql.Timestamp;
import java.time.Instant;
import java.util.ArrayList;
import java.util.List;
import java.util.Optional;
import java.util.UUID;

@Service
@RequiredArgsConstructor
Expand Down Expand Up @@ -126,6 +127,17 @@ public Long saveQuery(Long queryId, String userId, SavedQuery savedQueryApi) {
return savedQueryRepository.save(savedQuery).getId();
}

public void updateSavedQuery(Long queryId, SavedQuery savedQuery) throws QueryNotFoundException {
Optional<de.numcodex.feasibility_gui_backend.query.persistence.SavedQuery> savedQueryOptional = savedQueryRepository.findByQueryId(queryId);
if (savedQueryOptional.isEmpty()) {
throw new QueryNotFoundException();
}
var oldSavedQuery = savedQueryOptional.get();
oldSavedQuery.setLabel(savedQuery.label());
oldSavedQuery.setComment(savedQuery.comment());
savedQueryRepository.save(oldSavedQuery);
}

public de.numcodex.feasibility_gui_backend.query.persistence.QueryTemplate getQueryTemplate(
Long queryId, String authorId) throws QueryTemplateException {
de.numcodex.feasibility_gui_backend.query.persistence.QueryTemplate queryTemplate = queryTemplateRepository.findById(
Expand All @@ -141,6 +153,36 @@ public List<de.numcodex.feasibility_gui_backend.query.persistence.QueryTemplate>
return queryTemplateRepository.findByAuthor(authorId);
}

public void updateQueryTemplate(Long queryTemplateId, QueryTemplate queryTemplate, String authorId) throws QueryTemplateException {
var templates = getQueryTemplatesForAuthor(authorId);
Optional<de.numcodex.feasibility_gui_backend.query.persistence.QueryTemplate> templateToUpdate = templates.stream().
filter(t -> t.getId().equals(queryTemplateId)).
findFirst();

if (templateToUpdate.isPresent()) {
var template = templateToUpdate.get();
template.setLabel(queryTemplate.label());
template.setComment(queryTemplate.comment());
template.setLastModified(Timestamp.from(Instant.now()));
queryTemplateRepository.save(template);
} else {
throw new QueryTemplateException("not found");
}
}

public void deleteQueryTemplate(Long queryTemplateId, String authorId) throws QueryTemplateException {
var templates = getQueryTemplatesForAuthor(authorId);
Optional<de.numcodex.feasibility_gui_backend.query.persistence.QueryTemplate> templateToDelete = templates.stream().
filter(t -> t.getId().equals(queryTemplateId)).
findFirst();

if (templateToDelete.isPresent()) {
queryTemplateRepository.delete(templateToDelete.get());
} else {
throw new QueryTemplateException("not found");
}
}

public QueryTemplate convertTemplatePersistenceToApi(
de.numcodex.feasibility_gui_backend.query.persistence.QueryTemplate in)
throws JsonProcessingException {
Expand Down Expand Up @@ -172,6 +214,7 @@ private de.numcodex.feasibility_gui_backend.query.persistence.SavedQuery convert
out.setQuery(queryRepository.getReferenceById(queryId));
out.setComment(in.comment());
out.setLabel(in.label());
out.setResultSize(in.totalNumberOfPatients());
return out;
}

Expand Down Expand Up @@ -201,6 +244,8 @@ public List<QueryListEntry> convertQueriesToQueryListEntries(List<de.numcodex.fe
QueryListEntry.builder()
.id(q.getId())
.label(q.getSavedQuery().getLabel())
.comment(q.getSavedQuery().getComment())
.totalNumberOfPatients(q.getSavedQuery().getResultSize())
.createdAt(q.getCreatedAt())
.build());
} else {
Expand All @@ -220,6 +265,24 @@ public Long getAmountOfQueriesByUserAndInterval(String userId, int minutes) {
}

public Long getRetryAfterTime(String userId, int offset, long interval) {
return 60 * interval - queryRepository.getAgeOfNToLastQueryInSeconds(userId, offset) + 1;
try {
return 60 * interval - queryRepository.getAgeOfNToLastQueryInSeconds(userId, offset) + 1;
} catch (NullPointerException e) {
return 0L;
}
}

public Long getAmountOfSavedQueriesByUser(String userId) {
var queries = queryRepository.findSavedQueriesByAuthor(userId);
return queries.map(queryList -> (long) queryList.size()).orElse(0L);
}

public void deleteSavedQuery(Long queryId) throws QueryNotFoundException {
var savedQueryOptional = savedQueryRepository.findByQueryId(queryId);
if (savedQueryOptional.isPresent()) {
savedQueryRepository.deleteById(savedQueryOptional.get().getId());
} else {
throw new QueryNotFoundException();
}
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -12,7 +12,9 @@
public record QueryListEntry(
@JsonProperty long id,
@JsonProperty String label,
@JsonProperty Timestamp createdAt
@JsonProperty String comment,
@JsonProperty Timestamp createdAt,
@JsonProperty Long totalNumberOfPatients
) {

}
Original file line number Diff line number Diff line change
Expand Up @@ -9,7 +9,8 @@
@Builder
public record SavedQuery(
@JsonProperty String label,
@JsonProperty String comment
@JsonProperty String comment,
@JsonProperty Long totalNumberOfPatients
) {

}
Original file line number Diff line number Diff line change
Expand Up @@ -12,7 +12,8 @@ public enum FeasibilityIssue {
QUOTA_EXCEEDED(10002, "Too many requests - quota reached", IssueType.BUSY, Severity.ERROR),
POLLING_LIMIT_EXCEEDED(10003, "Too many requests - polling limit exceeded", IssueType.BUSY, Severity.ERROR),
PRIVACY_RESTRICTION_RESULT_SIZE(10004, "Total number of results below threshold", IssueType.BUSY, Severity.ERROR),
PRIVACY_RESTRICTION_RESULT_SITES(10005, "Too few responding sites", IssueType.BUSY, Severity.ERROR);
PRIVACY_RESTRICTION_RESULT_SITES(10005, "Too few responding sites", IssueType.BUSY, Severity.ERROR),
SAVED_QUERY_STORAGE_FULL(10006, "Saved query limit reached. Please delete old saved queries before trying to create new ones.", IssueType.FORBIDDEN, Severity.ERROR);

private static final FeasibilityIssue[] VALUES;

Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,14 @@
package de.numcodex.feasibility_gui_backend.query.api.status;

import com.fasterxml.jackson.annotation.JsonInclude;
import com.fasterxml.jackson.annotation.JsonProperty;
import lombok.Builder;

@JsonInclude()
@Builder
public record SavedQuerySlots(
@JsonProperty("used") long used,
@JsonProperty("total") long total
)
{
}
Original file line number Diff line number Diff line change
Expand Up @@ -78,6 +78,7 @@ public List<String> getResultSiteIds(String brokerQueryId) throws QueryNotFoundE
return findQuery(brokerQueryId).hasResult() ? Collections.singletonList(SITE_ID_LOCAL) : Collections.emptyList();
}

@Override
public String getSiteName(String siteId) throws SiteNotFoundException {
if (SITE_ID_LOCAL.equals(siteId)) {
return SITE_NAME_LOCAL;
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -27,7 +27,7 @@ public class Query {
@Column(name = "created_by", updatable = false)
private String createdBy;

@ManyToOne(fetch = FetchType.LAZY)
@ManyToOne(fetch = FetchType.LAZY, cascade = CascadeType.ALL)
@JoinColumn(referencedColumnName = "id", name = "query_content_id")
private QueryContent queryContent;

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -23,12 +23,12 @@ public class SavedQuery {
@OneToOne(fetch = FetchType.LAZY)
private Query query;

@Column(name = "deleted")
private Timestamp deleted;

@Column(name = "label", nullable = false)
private String label;

@Column(name = "comment")
private String comment;

@Column(name = "result_size")
private Long resultSize;
}
Original file line number Diff line number Diff line change
Expand Up @@ -103,6 +103,7 @@ Translator createCqlTranslator(@Qualifier("translation") ObjectMapper jsonUtil)
"frailtyscore"),
entry("http://terminology.hl7.org/CodeSystem/consentcategorycodes", "consentcategory"),
entry("urn:oid:2.16.840.1.113883.3.1937.777.24.5.3", "consent"),
entry("http://hl7.org/fhir/sid/icd-o-3", "icdo3"),
entry("http://hl7.org/fhir/consent-provision-type", "provisiontype"))));
}

Expand Down
Loading

0 comments on commit 0114da9

Please sign in to comment.