reduce method
The reduce
method is the action reducer. It may read the action state,
the store state, and then return a new state (or null
if no state
change is necessary).
It may be synchronous (returning AppState
or null
)
or async (returning Future<AppState>
or Future<null>
).
The StoreConnector
s may rebuild only if the reduce
method returns
a state which is both not null
and different from the previous one
(comparing by identical
, not equals
).
Implementation
@override
Future<CoreState?> reduce() async {
if (client == null) {
throw const UserException('cannot start a visit');
}
final Map<String, dynamic> input = <String, dynamic>{
'input': <String, dynamic>{
'patientID': breakGlassEpisodeCreationInput?.patientID,
'providerCode': breakGlassEpisodeCreationInput?.providerCode,
'practitionerUID': breakGlassEpisodeCreationInput?.practitionerUID,
'providerPhone': breakGlassEpisodeCreationInput?.providerPhone,
'otp': breakGlassEpisodeCreationInput?.otp,
'fullAccess': false,
'patientPhone': breakGlassEpisodeCreationInput?.patientPhone,
}
};
final http.Response result =
await client!.query(startBreakGlassVisitMutation, input);
if (result.statusCode != 200) {
throw const UserException(
'Failed to start a visit, check internet connection');
}
final Map<String, dynamic> data = client!.toMap(result);
client!.close();
final String? error = client!.parseError(data);
if (error != null) {
await captureException(
errorStartingVisitEmergency,
query: startBreakGlassVisitMutation,
error: error,
response: data,
variables: input,
);
throw const UserException(
'Failed to start a visit, unexpected error occurred'); // todo: create better messages
}
final EpisodeOfCarePayload episodeOfCarePayload =
EpisodeOfCarePayload.fromJson(
data['data']['startEpisodeByBreakGlass'] as Map<String, dynamic>);
// save the open episode of care into the core state
final ClinicalState? clinicalState = state.clinicalState?.copyWith
.call(currentEpisodeOfCare: episodeOfCarePayload.episodeOfCare);
final CoreState newState =
state.copyWith.call(clinicalState: clinicalState);
// for backward compatibility only
// TODO: REMOVE AFTER REFACTORING PATIENT PROFILE
final CurrentPatientInEpisode currentPatientInEpisode =
CurrentPatientInEpisode();
currentPatientInEpisode.fullAccess.add(false);
currentPatientInEpisode.episodeOfCarePayload.add(episodeOfCarePayload);
final PatientEdge patientEdge =
PatientEdge(node: state.clinicalState?.patientPayload?.patientRecord);
final List<PatientEdge?> list = List<PatientEdge?>.empty(growable: true);
list.add(patientEdge);
final PatientConnection patientConnection = PatientConnection(edges: list);
currentPatientInEpisode.patientConnection.add(patientConnection);
dispatch(
NavigateAction<CoreState>.popAndPushNamed(patientProfilePageRoute));
return newState;
}