For tracking expected data (#353) we need to persist actual observation instances for study participants.
The currently modeled observations are configurations that can be used to calculate what actual observations each participant of a study is expected to perform. This information is sufficient for the study manager and the participant application to materialize observations on demand, but as we start to track information for actual observation instances like the data health and need to perform actions on those information like sending alerts, we need a way to persist information for observation instances.
Additionally if studies are paused and re-configured one could end up in a situation, where existing observation data does no longer confirm with the changed configuration.
Provide Storage and Access for ParticipantObservations
A ParticipantObservation is an occurrence of an observation for a study of an study participant. It is
- linked to a study (direct or indirect)
- to an participant of that study
- to an configured observation of that study
- it has an starting timestamp that is
<= the current time
- it has an end timestamp
- it has an data state (missing, partial, incomplete, invalid, complete)
- it has an temporal state (active, complete) - transient - calculated based on start/end timestamps
- it can store or link to actions performed (e.g. Notifications)
ParticipantObservationService to:
- CRUD ParticipantObservations
- Upsert by ObservationId, ParticipantId, startTimestamp and endTimestamp
- Query for ParticipantObservation by data state
- Update the data state of a ParticipantObservation
Periodic Job to create ParticipantObservation
We need to periodically create ParticipantObservation instances for Participants based on the current time. For that one needs to iterate over all participants of an study, materialize observations based on the current configuration and create ParticipantObservation instances for active Observations that do not already exist. The ParticipantObservationService shall provide a special upsert method for this task.
Periodic Job to validate the Data Health of ParticipantObservation
We need to periodically validate data health for ParticipantObservation that are not yet in the data states completed or invalid. For such ParticipantObservations this component needs to
- retrieve data from the elastic index
- if no data are available set the data state to missing
- use the Observation module to check the validity of the present data. This module can set the state to
- partial: if some data are missing (e.g. if temporal data started late
- invalid: if the available data are not as expected
- incomplete: if all data are available and valid, but the observation is ongoing and therefore additional data are expected
- complete: if the available data is valid and complete
NOTE: The validation of received data is the responsibility of the Observation Module. The Observation code needs to provide a functionality to validate received data. A default implementation that simply validates the existence of any data shall be provided as a reasonable default for modules that do not provide this functionality
In addition this component needs to create Notifications for ParticipantObservation that do not have valid data. For that a configuration shall be created that allows to configure after what timespan notifications are triggered.
TODO: We might store Notifications in an own database table - especially when we want to track the status of notifications of if we want to remove unread notifications if data does become available after a notification was already created.
For tracking expected data (#353) we need to persist actual observation instances for study participants.
The currently modeled observations are configurations that can be used to calculate what actual observations each participant of a study is expected to perform. This information is sufficient for the study manager and the participant application to materialize observations on demand, but as we start to track information for actual observation instances like the data health and need to perform actions on those information like sending alerts, we need a way to persist information for observation instances.
Additionally if studies are paused and re-configured one could end up in a situation, where existing observation data does no longer confirm with the changed configuration.
Provide Storage and Access for ParticipantObservations
A ParticipantObservation is an occurrence of an observation for a study of an study participant. It is
<=the current timeParticipantObservationService to:
Periodic Job to create ParticipantObservation
We need to periodically create ParticipantObservation instances for Participants based on the current time. For that one needs to iterate over all participants of an study, materialize observations based on the current configuration and create ParticipantObservation instances for active Observations that do not already exist. The
ParticipantObservationServiceshall provide a specialupsertmethod for this task.Periodic Job to validate the Data Health of ParticipantObservation
We need to periodically validate data health for ParticipantObservation that are not yet in the data states
completedorinvalid. For such ParticipantObservations this component needs toNOTE: The validation of received data is the responsibility of the Observation Module. The Observation code needs to provide a functionality to validate received data. A default implementation that simply validates the existence of any data shall be provided as a reasonable default for modules that do not provide this functionality
In addition this component needs to create Notifications for ParticipantObservation that do not have valid data. For that a configuration shall be created that allows to configure after what timespan notifications are triggered.
TODO: We might store Notifications in an own database table - especially when we want to track the status of notifications of if we want to remove unread notifications if data does become available after a notification was already created.