From 6a95fa0077dd27f49213c0dbd2b86566d0520e59 Mon Sep 17 00:00:00 2001 From: EmmaLRussell Date: Sun, 5 Nov 2023 13:59:00 +0000 Subject: [PATCH] display model fit error --- app/static/src/app/components/fit/FitTab.vue | 9 +++++ app/static/src/app/serialise.ts | 3 +- .../src/app/store/appState/mutations.ts | 3 +- app/static/src/app/store/modelFit/actions.ts | 40 ++++++++++--------- app/static/src/app/store/modelFit/modelFit.ts | 3 +- .../src/app/store/modelFit/mutations.ts | 12 +++++- app/static/src/app/store/modelFit/state.ts | 2 + .../src/app/types/serialisationTypes.ts | 3 +- app/static/src/app/userMessages.ts | 1 + 9 files changed, 52 insertions(+), 24 deletions(-) diff --git a/app/static/src/app/components/fit/FitTab.vue b/app/static/src/app/components/fit/FitTab.vue index e0577c0f7..c8d6b7566 100644 --- a/app/static/src/app/components/fit/FitTab.vue +++ b/app/static/src/app/components/fit/FitTab.vue @@ -21,6 +21,7 @@
{{cancelledMsg}}
+ @@ -39,10 +40,12 @@ import { ModelFitMutation } from "../../store/modelFit/mutations"; import { fitRequirementsExplanation, fitUpdateRequiredExplanation } from "./support"; import { allTrue, anyTrue } from "../../utils"; import LoadingButton from "../LoadingButton.vue"; +import ErrorInfo from "@/app/components/ErrorInfo.vue"; export default defineComponent({ name: "FitTab", components: { + ErrorInfo, LoadingSpinner, FitPlot, ActionRequiredMessage, @@ -57,6 +60,7 @@ export default defineComponent({ const canFitModel = computed(() => allTrue(fitRequirements.value)); const compileRequired = computed(() => store.state.model.compileRequired); const fitUpdateRequired = computed(() => store.state.modelFit.fitUpdateRequired); + const error = computed(() => store.state.modelFit.error); const fitModel = () => store.dispatch(`${namespace}/${ModelFitAction.FitModel}`); const cancelFit = () => store.commit(`${namespace}/${ModelFitMutation.SetFitting}`, false); @@ -68,6 +72,10 @@ export default defineComponent({ const sumOfSquares = computed(() => store.state.modelFit.sumOfSquares); const actionRequiredMessage = computed(() => { + if (error.value) { + return userMessages.modelFit.errorOccurred; + } + if (!allTrue(fitRequirements.value)) { return fitRequirementsExplanation(fitRequirements.value); } @@ -119,6 +127,7 @@ export default defineComponent({ cancelledMsg, sumOfSquares, actionRequiredMessage, + error, iconType, iconClass }; diff --git a/app/static/src/app/serialise.ts b/app/static/src/app/serialise.ts index 7585566c4..f768e98a4 100644 --- a/app/static/src/app/serialise.ts +++ b/app/static/src/app/serialise.ts @@ -130,7 +130,8 @@ function serialiseModelFit(modelFit: ModelFitState): SerialisedModelFitState { converged: modelFit.converged, sumOfSquares: modelFit.sumOfSquares, paramsToVary: modelFit.paramsToVary, - result: serialiseSolutionResult(modelFit.result) + result: serialiseSolutionResult(modelFit.result), + error: modelFit.error }; } diff --git a/app/static/src/app/store/appState/mutations.ts b/app/static/src/app/store/appState/mutations.ts index 67128a618..93de9390e 100644 --- a/app/static/src/app/store/appState/mutations.ts +++ b/app/static/src/app/store/appState/mutations.ts @@ -21,7 +21,8 @@ export enum AppStateMutation { export const StateUploadMutations = [ AppStateMutation.ClearQueuedStateUpload, AppStateMutation.SetQueuedStateUpload, - AppStateMutation.SetStateUploadInProgress + AppStateMutation.SetStateUploadInProgress, + AppStateMutation.SetPersisted ] as string[]; export const appStateMutations: MutationTree = { diff --git a/app/static/src/app/store/modelFit/actions.ts b/app/static/src/app/store/modelFit/actions.ts index a7c8ca8e2..6dd584308 100644 --- a/app/static/src/app/store/modelFit/actions.ts +++ b/app/static/src/app/store/modelFit/actions.ts @@ -50,24 +50,28 @@ export const actions: ActionTree = { const { advancedSettings } = rootState.run; const advancedSettingsOdin = convertAdvancedSettingsToOdin(advancedSettings, pars.base); - const simplex = odinRunnerOde!.wodinFit( - odin!, - data, - pars, - linkedVariable, - advancedSettingsOdin, - {} - ); - - const inputs = { - data, - endTime, - link - }; - - commit(ModelFitMutation.SetFitUpdateRequired, null); - commit(ModelFitMutation.SetInputs, inputs); - dispatch(ModelFitAction.FitModelStep, simplex); + try { + const simplex = odinRunnerOde!.wodinFit( + odin!, + data, + pars, + linkedVariable, + advancedSettingsOdin, + {} + ); + + const inputs = { + data, + endTime, + link + }; + commit(ModelFitMutation.SetFitUpdateRequired, null); + commit(ModelFitMutation.SetInputs, inputs); + dispatch(ModelFitAction.FitModelStep, simplex); + } catch (e: unknown) { + commit(ModelFitMutation.SetError, {error: "Model fit error", detail: (e as Error).message}); + commit(ModelFitMutation.SetFitting, false); + } } }, diff --git a/app/static/src/app/store/modelFit/modelFit.ts b/app/static/src/app/store/modelFit/modelFit.ts index a5bca25b3..0048dc8c6 100644 --- a/app/static/src/app/store/modelFit/modelFit.ts +++ b/app/static/src/app/store/modelFit/modelFit.ts @@ -18,7 +18,8 @@ export const defaultState: ModelFitState = { sumOfSquares: null, paramsToVary: [], inputs: null, - result: null + result: null, + error: null }; export const modelFit = { diff --git a/app/static/src/app/store/modelFit/mutations.ts b/app/static/src/app/store/modelFit/mutations.ts index 976ec1e88..d8ed59750 100644 --- a/app/static/src/app/store/modelFit/mutations.ts +++ b/app/static/src/app/store/modelFit/mutations.ts @@ -1,6 +1,6 @@ import { MutationTree } from "vuex"; import { ModelFitInputs, ModelFitState, FitUpdateRequiredReasons } from "./state"; -import { SimplexResult } from "../../types/responseTypes"; +import {SimplexResult, WodinError} from "../../types/responseTypes"; export enum ModelFitMutation { SetFitting = "SetFitting", @@ -8,12 +8,16 @@ export enum ModelFitMutation { SetInputs = "SetInputs", SetParamsToVary = "SetParamsToVary", SetSumOfSquares = "SetSumOfSquares", - SetFitUpdateRequired = "SetFitUpdateRequired" + SetFitUpdateRequired = "SetFitUpdateRequired", + SetError = "SetError" } export const mutations: MutationTree = { [ModelFitMutation.SetFitting](state: ModelFitState, payload: boolean) { state.fitting = payload; + if (payload) { + state.error = null + } }, [ModelFitMutation.SetResult](state: ModelFitState, payload: SimplexResult) { @@ -43,6 +47,10 @@ export const mutations: MutationTree = { state.sumOfSquares = payload; }, + [ModelFitMutation.SetError](state: ModelFitState, payload: WodinError) { + state.error = payload; + }, + [ModelFitMutation.SetFitUpdateRequired](state: ModelFitState, payload: null | Partial) { if (payload === null) { state.fitUpdateRequired = { diff --git a/app/static/src/app/store/modelFit/state.ts b/app/static/src/app/store/modelFit/state.ts index e2fe35acf..33ebe3fec 100644 --- a/app/static/src/app/store/modelFit/state.ts +++ b/app/static/src/app/store/modelFit/state.ts @@ -1,5 +1,6 @@ import { OdinFitResult } from "../../types/wrapperTypes"; import type { FitData, FitDataLink } from "../fitData/state"; +import {WodinError} from "../../types/responseTypes"; export interface ModelFitInputs { data: FitData; @@ -25,6 +26,7 @@ export interface ModelFitState { paramsToVary: string[], inputs: ModelFitInputs | null, // all inputs except parameters, which vary result: OdinFitResult | null, // full solution for current best fit, + error: null | WodinError } export interface ModelFitRequirements { diff --git a/app/static/src/app/types/serialisationTypes.ts b/app/static/src/app/types/serialisationTypes.ts index 19fc54d5e..8f242a946 100644 --- a/app/static/src/app/types/serialisationTypes.ts +++ b/app/static/src/app/types/serialisationTypes.ts @@ -77,7 +77,8 @@ export interface SerialisedModelFitState { converged: boolean | null, sumOfSquares: number | null, paramsToVary: string[], - result: SerialisedRunResult | null + result: SerialisedRunResult | null, + error: null | WodinError } export interface SerialisedAppState { diff --git a/app/static/src/app/userMessages.ts b/app/static/src/app/userMessages.ts index d6c9968c9..f4c43cf1e 100644 --- a/app/static/src/app/userMessages.ts +++ b/app/static/src/app/userMessages.ts @@ -56,6 +56,7 @@ export default { notFittedYet: "Model has not been fitted.", selectParamToVary: "Please select at least one parameter to vary during model fit.", compileRequired: "Model code has been updated. Compile code and Fit Model for updated best fit.", + errorOccurred: "An error occurred during model fit.", updateFitReasons: { prefix: "Fit is out of date:", unknown: "unknown reasons, contact the administrator, as this is unexpected",