Skip to content

Commit b9f2ba4

Browse files
authored
fix(app): change error text when creation error is run is busy (#11069)
closes #11060
1 parent ace77fd commit b9f2ba4

File tree

6 files changed

+101
-4
lines changed

6 files changed

+101
-4
lines changed

app/src/assets/localization/en/shared.json

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -34,5 +34,6 @@
3434
"robot_was_seen_but_is_unreachable": "This robot has been seen recently, but is currently not reachable at IP address {{hostname}}",
3535
"protocol_run_general_error_msg": "Protocol run could not be created on the robot.",
3636
"proceed_to_setup": "Proceed to setup",
37-
"a_software_update_is_available": "A software update is available for this robot. Update to run protocols."
37+
"a_software_update_is_available": "A software update is available for this robot. Update to run protocols.",
38+
"robot_is_busy_no_protocol_run_allowed": "This robot is busy and can’t run this protocol right now. <robotLink>Go to Robot</robotLink>"
3839
}

app/src/organisms/ChooseProtocolSlideout/__tests__/ChooseProtocolSlideout.test.tsx

Lines changed: 26 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -109,6 +109,7 @@ describe('ChooseProtocolSlideout', () => {
109109
createRunFromProtocolSource: mockCreateRunFromProtocol,
110110
isCreatingRun: false,
111111
reset: jest.fn(),
112+
runCreationErrorCode: 'error code',
112113
})
113114
const [{ getByRole, getByText }] = render({
114115
robot: mockConnectableRobot,
@@ -123,4 +124,29 @@ describe('ChooseProtocolSlideout', () => {
123124
})
124125
expect(getByText('run creation error')).toBeInTheDocument()
125126
})
127+
128+
it('renders error state when run creation error code is 409', () => {
129+
mockUseCreateRunFromProtocol.mockReturnValue({
130+
runCreationError: 'Current run is not idle or stopped.',
131+
createRunFromProtocolSource: mockCreateRunFromProtocol,
132+
isCreatingRun: false,
133+
reset: jest.fn(),
134+
runCreationErrorCode: '409',
135+
})
136+
const [{ getByRole, getByText }] = render({
137+
robot: mockConnectableRobot,
138+
onCloseClick: jest.fn(),
139+
showSlideout: true,
140+
})
141+
const proceedButton = getByRole('button', { name: 'Proceed to setup' })
142+
proceedButton.click()
143+
expect(mockCreateRunFromProtocol).toHaveBeenCalledWith({
144+
files: [expect.any(File)],
145+
protocolKey: storedProtocolDataFixture.protocolKey,
146+
})
147+
getByText('This robot is busy and can’t run this protocol right now.')
148+
const link = getByRole('link', { name: 'Go to Robot' })
149+
fireEvent.click(link)
150+
expect(link.getAttribute('href')).toEqual('/devices/opentrons-robot-name')
151+
})
126152
})

app/src/organisms/ChooseProtocolSlideout/index.tsx

Lines changed: 22 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -2,9 +2,10 @@ import * as React from 'react'
22
import path from 'path'
33
import first from 'lodash/first'
44
import { Trans, useTranslation } from 'react-i18next'
5-
import { Link, useHistory } from 'react-router-dom'
5+
import { Link, NavLink, useHistory } from 'react-router-dom'
66
import { ApiHostProvider } from '@opentrons/react-api-client'
77
import { useSelector } from 'react-redux'
8+
import { css } from 'styled-components'
89

910
import {
1011
SPACING,
@@ -69,6 +70,7 @@ export function ChooseProtocolSlideout(
6970
runCreationError,
7071
isCreatingRun,
7172
reset: resetCreateRun,
73+
runCreationErrorCode,
7274
} = useCreateRunFromProtocol({
7375
onSuccess: ({ data: runData }) => {
7476
history.push(`/devices/${name}/protocol-runs/${runData.id}`)
@@ -172,7 +174,25 @@ export function ChooseProtocolSlideout(
172174
marginTop={`-${SPACING.spacing2}`}
173175
marginBottom={SPACING.spacing3}
174176
>
175-
{runCreationError}
177+
{runCreationErrorCode === '409' ? (
178+
<Trans
179+
t={t}
180+
i18nKey="shared:robot_is_busy_no_protocol_run_allowed"
181+
components={{
182+
robotLink: (
183+
<NavLink
184+
css={css`
185+
color: ${COLORS.errorText};
186+
text-decoration: ${TYPOGRAPHY.textDecorationUnderline};
187+
`}
188+
to={`/devices/${robot.name}`}
189+
/>
190+
),
191+
}}
192+
/>
193+
) : (
194+
runCreationError
195+
)}
176196
</StyledText>
177197
) : null}
178198
</Flex>

app/src/organisms/ChooseRobotSlideout/__tests__/ChooseRobotSlideout.test.tsx

Lines changed: 26 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -227,6 +227,7 @@ describe('ChooseRobotSlideout', () => {
227227
createRunFromProtocolSource: mockCreateRunFromProtocolSource,
228228
isCreatingRun: false,
229229
reset: jest.fn(),
230+
runCreationErrorCode: 'error code',
230231
})
231232
const [{ getByRole, getByText }] = render({
232233
storedProtocolData: storedProtocolDataFixture,
@@ -241,4 +242,29 @@ describe('ChooseRobotSlideout', () => {
241242
})
242243
expect(getByText('run creation error')).toBeInTheDocument()
243244
})
245+
246+
it('renders error state when run creation error code is 409', () => {
247+
mockUseCreateRunFromProtocol.mockReturnValue({
248+
runCreationError: 'Current run is not idle or stopped.',
249+
createRunFromProtocolSource: mockCreateRunFromProtocolSource,
250+
isCreatingRun: false,
251+
reset: jest.fn(),
252+
runCreationErrorCode: '409',
253+
})
254+
const [{ getByRole, getByText }] = render({
255+
storedProtocolData: storedProtocolDataFixture,
256+
onCloseClick: jest.fn(),
257+
showSlideout: true,
258+
})
259+
const proceedButton = getByRole('button', { name: 'Proceed to setup' })
260+
proceedButton.click()
261+
expect(mockCreateRunFromProtocolSource).toHaveBeenCalledWith({
262+
files: [expect.any(File)],
263+
protocolKey: storedProtocolDataFixture.protocolKey,
264+
})
265+
getByText('This robot is busy and can’t run this protocol right now.')
266+
const link = getByRole('link', { name: 'Go to Robot' })
267+
fireEvent.click(link)
268+
expect(link.getAttribute('href')).toEqual('/devices/opentrons-robot-name')
269+
})
244270
})

app/src/organisms/ChooseRobotSlideout/index.tsx

Lines changed: 21 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -4,6 +4,7 @@ import first from 'lodash/first'
44
import { useTranslation, Trans } from 'react-i18next'
55
import { useSelector, useDispatch } from 'react-redux'
66
import { NavLink, useHistory } from 'react-router-dom'
7+
import { css } from 'styled-components'
78

89
import {
910
SPACING,
@@ -75,6 +76,7 @@ export function ChooseRobotSlideout(
7576
runCreationError,
7677
reset: resetCreateRun,
7778
isCreatingRun,
79+
runCreationErrorCode,
7880
} = useCreateRunFromProtocol(
7981
{
8082
onSuccess: ({ data: runData }) => {
@@ -221,7 +223,25 @@ export function ChooseRobotSlideout(
221223
marginTop={`-${SPACING.spacing2}`}
222224
marginBottom={SPACING.spacing3}
223225
>
224-
{runCreationError}
226+
{runCreationErrorCode === '409' ? (
227+
<Trans
228+
t={t}
229+
i18nKey="shared:robot_is_busy_no_protocol_run_allowed"
230+
components={{
231+
robotLink: (
232+
<NavLink
233+
css={css`
234+
color: ${COLORS.errorText};
235+
text-decoration: ${TYPOGRAPHY.textDecorationUnderline};
236+
`}
237+
to={`/devices/${robot.name}`}
238+
/>
239+
),
240+
}}
241+
/>
242+
) : (
243+
runCreationError
244+
)}
225245
</StyledText>
226246
)}
227247
</Flex>

app/src/organisms/ChooseRobotSlideout/useCreateRunFromProtocol.ts

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -24,6 +24,7 @@ export interface UseCreateRun {
2424
>
2525
isCreatingRun: boolean
2626
runCreationError: string | null
27+
runCreationErrorCode: string | null
2728
reset: () => void
2829
}
2930

@@ -84,6 +85,8 @@ export function useCreateRunFromProtocol(
8485
error != null && console.error(error)
8586
error = error?.length > 255 ? t('protocol_run_general_error_msg') : error
8687

88+
const errorCode = protocolError?.code ?? runError?.code ?? null
89+
8790
return {
8891
createRunFromProtocolSource: (
8992
{ files: srcFiles, protocolKey },
@@ -97,6 +100,7 @@ export function useCreateRunFromProtocol(
97100
},
98101
isCreatingRun: isCreatingProtocol || isCreatingRun,
99102
runCreationError: error,
103+
runCreationErrorCode: errorCode,
100104
reset: () => {
101105
resetProtocolMutation()
102106
resetRunMutation()

0 commit comments

Comments
 (0)