Skip to content

Commit 5520927

Browse files
committed
Rewrite miri reducer with RTK
1 parent 8c28212 commit 5520927

File tree

7 files changed

+63
-64
lines changed

7 files changed

+63
-64
lines changed

ui/frontend/.eslintrc.js

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -82,6 +82,7 @@ module.exports = {
8282
'reducers/output/llvmIr.ts',
8383
'reducers/output/meta.ts',
8484
'reducers/output/mir.ts',
85+
'reducers/output/miri.ts',
8586
'reducers/output/wasm.ts',
8687
'reducers/versions.ts',
8788
'reducers/websocket.ts',

ui/frontend/.prettierignore

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -33,6 +33,7 @@ node_modules
3333
!reducers/output/llvmIr.ts
3434
!reducers/output/meta.ts
3535
!reducers/output/mir.ts
36+
!reducers/output/miri.ts
3637
!reducers/output/wasm.ts
3738
!reducers/versions.ts
3839
!reducers/websocket.ts

ui/frontend/ToolsMenu.tsx

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -10,6 +10,7 @@ import * as actions from './actions';
1010
import { useAppDispatch } from './configureStore';
1111
import { performFormat } from './reducers/output/format';
1212
import { performClippy } from './reducers/output/clippy';
13+
import { performMiri } from './reducers/output/miri';
1314

1415
interface ToolsMenuProps {
1516
close: () => void;
@@ -31,7 +32,7 @@ const ToolsMenu: React.FC<ToolsMenuProps> = props => {
3132
props.close();
3233
}, [dispatch, props]);
3334
const miri = useCallback(() => {
34-
dispatch(actions.performMiri());
35+
dispatch(performMiri());
3536
props.close();
3637
}, [dispatch, props]);
3738
const format = useCallback(() => {

ui/frontend/actions.ts

Lines changed: 0 additions & 46 deletions
Original file line numberDiff line numberDiff line change
@@ -83,9 +83,6 @@ export enum ActionType {
8383
EnableFeatureGate = 'ENABLE_FEATURE_GATE',
8484
GotoPosition = 'GOTO_POSITION',
8585
SelectText = 'SELECT_TEXT',
86-
RequestMiri = 'REQUEST_MIRI',
87-
MiriSucceeded = 'MIRI_SUCCEEDED',
88-
MiriFailed = 'MIRI_FAILED',
8986
RequestMacroExpansion = 'REQUEST_MACRO_EXPANSION',
9087
MacroExpansionSucceeded = 'MACRO_EXPANSION_SUCCEEDED',
9188
MacroExpansionFailed = 'MACRO_EXPANSION_FAILED',
@@ -342,46 +339,6 @@ interface GeneralSuccess {
342339
stderr: string;
343340
}
344341

345-
const requestMiri = () =>
346-
createAction(ActionType.RequestMiri);
347-
348-
interface MiriRequestBody {
349-
code: string;
350-
edition: string;
351-
}
352-
353-
interface MiriResponseBody {
354-
success: boolean;
355-
stdout: string;
356-
stderr: string;
357-
}
358-
359-
type MiriSuccess = GeneralSuccess;
360-
361-
const receiveMiriSuccess = ({ stdout, stderr }: MiriSuccess) =>
362-
createAction(ActionType.MiriSucceeded, { stdout, stderr });
363-
364-
const receiveMiriFailure = ({ error }: GenericApiFailure) =>
365-
createAction(ActionType.MiriFailed, { error });
366-
367-
export function performMiri(): ThunkAction {
368-
// TODO: Check a cache
369-
return function(dispatch, getState) {
370-
dispatch(requestMiri());
371-
372-
const state = getState();
373-
const code = codeSelector(state);
374-
const { configuration: {
375-
edition,
376-
} } = state;
377-
const body: MiriRequestBody = { code, edition };
378-
379-
return jsonPost<MiriResponseBody>(routes.miri, body)
380-
.then(json => dispatch(receiveMiriSuccess(json)))
381-
.catch(json => dispatch(receiveMiriFailure(json)));
382-
};
383-
}
384-
385342
const requestMacroExpansion = () =>
386343
createAction(ActionType.RequestMacroExpansion);
387344

@@ -557,9 +514,6 @@ export type Action =
557514
| ReturnType<typeof enableFeatureGate>
558515
| ReturnType<typeof gotoPosition>
559516
| ReturnType<typeof selectText>
560-
| ReturnType<typeof requestMiri>
561-
| ReturnType<typeof receiveMiriSuccess>
562-
| ReturnType<typeof receiveMiriFailure>
563517
| ReturnType<typeof requestMacroExpansion>
564518
| ReturnType<typeof receiveMacroExpansionSuccess>
565519
| ReturnType<typeof receiveMacroExpansionFailure>

ui/frontend/reducers/output/meta.ts

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -11,6 +11,7 @@ import { performGistLoad, performGistSave } from './gist';
1111
import { performCompileHir } from './hir';
1212
import { performCompileLlvmIr } from './llvmIr';
1313
import { performCompileMir } from './mir';
14+
import { performMiri } from './miri';
1415
import { performCompileWasm } from './wasm';
1516

1617
const initialState: State = {};
@@ -40,7 +41,7 @@ const slice = createSlice({
4041
state.focus = Focus.Clippy;
4142
})
4243

43-
.addCase(ActionType.RequestMiri, (state) => {
44+
.addCase(performMiri.pending, (state) => {
4445
state.focus = Focus.Miri;
4546
})
4647

ui/frontend/reducers/output/miri.ts

Lines changed: 51 additions & 16 deletions
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,13 @@
1-
import { Action, ActionType } from '../../actions';
2-
import { finish, start } from './sharedStateManagement';
1+
import { createAsyncThunk, createSlice } from '@reduxjs/toolkit';
2+
import * as z from 'zod';
33

4-
const DEFAULT: State = {
4+
import { adaptFetchError, jsonPost, routes } from '../../actions';
5+
import { miriRequestSelector } from '../../selectors';
6+
import RootState from '../../state';
7+
8+
const sliceName = 'output/miri';
9+
10+
const initialState: State = {
511
requestsInProgress: 0,
612
};
713

@@ -12,17 +18,46 @@ interface State {
1218
error?: string;
1319
}
1420

15-
export default function miri(state = DEFAULT, action: Action) {
16-
switch (action.type) {
17-
case ActionType.RequestMiri:
18-
return start(DEFAULT, state);
19-
case ActionType.MiriSucceeded: {
20-
const { stdout = '', stderr = '' } = action;
21-
return finish(state, { stdout, stderr });
22-
}
23-
case ActionType.MiriFailed:
24-
return finish(state, { error: action.error });
25-
default:
26-
return state;
27-
}
21+
interface MiriRequestBody {
22+
code: string;
23+
edition: string;
2824
}
25+
26+
const MiriResponseBody = z.object({
27+
success: z.boolean(),
28+
stdout: z.string(),
29+
stderr: z.string(),
30+
});
31+
32+
type MiriResponseBody = z.infer<typeof MiriResponseBody>;
33+
34+
export const performMiri = createAsyncThunk<MiriResponseBody, void, { state: RootState }>(
35+
sliceName,
36+
async (_arg: void, { getState }) => {
37+
const body: MiriRequestBody = miriRequestSelector(getState());
38+
39+
const d = await adaptFetchError(() => jsonPost(routes.miri, body));
40+
return MiriResponseBody.parseAsync(d);
41+
},
42+
);
43+
44+
const slice = createSlice({
45+
name: sliceName,
46+
initialState,
47+
reducers: {},
48+
extraReducers: (builder) => {
49+
builder
50+
.addCase(performMiri.pending, (state) => {
51+
state.requestsInProgress += 1;
52+
})
53+
.addCase(performMiri.fulfilled, (state, action) => {
54+
state.requestsInProgress -= 1;
55+
Object.assign(state, action.payload);
56+
})
57+
.addCase(performMiri.rejected, (state) => {
58+
state.requestsInProgress -= 1;
59+
});
60+
},
61+
});
62+
63+
export default slice.reducer;

ui/frontend/selectors/index.ts

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -333,6 +333,12 @@ export const formatRequestSelector = createSelector(
333333
(channel, edition, code) => ({ channel, edition, code }),
334334
);
335335

336+
export const miriRequestSelector = createSelector(
337+
editionSelector,
338+
codeSelector,
339+
(edition, code) => ({ edition, code }),
340+
);
341+
336342
const focus = (state: State) => state.output.meta.focus;
337343
export const isOutputFocused = createSelector(
338344
focus,

0 commit comments

Comments
 (0)