useReducer hook, ¿cómo se escribe comprobar la acción?
He estado buscando en varios recursos aquí en stackoverflow y no he encontrado nada (todavía) que solucione este problema que tengo. Tengo un conocimiento básico de mecanografiado, por lo que los errores me han limitado.
Si lo dejo action: anyen mi reductor, el error desaparece. Sin embargo, si lo escribo con Action, obtengo un error de sobrecarga. Todavía no soy lo suficientemente inteligente con TS para descubrir cómo razonar sobre esto o resolverlo, está pasando ReducerWithoutAction<any>, pero no tengo idea de cómo se supone que debo solucionarlo. Cualquier ayuda sería apreciada.
Voy a seguir husmeando mientras tanto.
// state types
type MainWrapperType = {
selection: number;
};
type Word = {
word: string;
translation: string;
wordTranscription: string;
partOfSpeech: string;
description: string;
example?: string;
};
type Notification = {
format: string;
message: string;
};
type Content = {
lessonName: string;
language: string;
topics: string[];
format: string;
file: File;
};
type InitialState = {
activeStep: number;
notification: Notification;
content: Content;
newWords: Word[];
initialTranscript: string;
modifiedTranscript: string;
transcriptSentences: string[];
};
const initialState = {
activeStep: 0,
notification: {
format: "",
message: "",
},
content: {
lessonName: "",
language: "",
topics: [],
format: "",
file: "",
},
newWords: [],
initialTranscript: "",
modifiedTranscript: "",
transcriptSentences: [],
};
// action types
interface SET_FILE {
type: "SET_FILE";
payload: File;
}
interface RESET_FILE {
type: "RESET_FILE";
}
interface SET_INIT_TRANSCRIPT {
type: "SET_INIT_TRANSCRIPT";
payload: string;
}
interface SET_MODIFIED_TRANSCRIPT {
type: "SET_MODIFIED_TRANSCRIPT";
payload: string;
}
interface ADD_SENTENCE {
type: "ADD_SENTENCE";
payload: string;
}
interface SET_SENTENCE_TRANSLATIONS {
type: "SET_SENTENCE_TRANSLATIONS";
payload: string[];
}
interface ADD_NEW_WORD {
type: "ADD_NEW_WORD";
payload: Word;
}
interface UPDATE_WORD {
type: "UPDATE_WORD";
payload: Word;
}
interface INCREMENT_ACTIVE_STEP {
type: "INCREMENT_ACTIVE_STEP";
}
interface DECREMENT_ACTIVE_STEP {
type: "DECREMENT_ACTIVE_STEP";
}
interface RESET_ACTIVE_STEP {
type: "RESET_ACTIVE_STEP";
}
interface RENDER_NOTIFICATION {
type: "RENDER_NOTIFICATION";
payload: Notification;
}
type Action =
| SET_FILE
| RESET_FILE
| SET_INIT_TRANSCRIPT
| SET_MODIFIED_TRANSCRIPT
| ADD_SENTENCE
| SET_SENTENCE_TRANSLATIONS
| ADD_NEW_WORD
| UPDATE_WORD
| INCREMENT_ACTIVE_STEP
| DECREMENT_ACTIVE_STEP
| RESET_ACTIVE_STEP
| RENDER_NOTIFICATION;
const reducer = (state: InitialState, action: Action) => {
switch (action.type) {
case "SET_FILE":
return { ...state, content: action.payload };
case "RESET_FILE":
return { ...state, content: initialState.content };
case "SET_INIT_TRANSCRIPT":
return { ...state, initialTranscript: action.payload };
case "SET_MODIFIED_TRANSCRIPT":
return { ...state, modifiedTranscript: action.payload };
case "ADD_SENTENCE":
return {
...state,
transcriptSentences: [...state.transcriptSentences, action.payload],
};
case "SET_SENTENCE_TRANSLATIONS":
return {
...state,
transcriptSentences: action.payload,
};
case "ADD_NEW_WORD":
return {
...state,
newWords: [...state.newWords, action.payload],
};
case "UPDATE_WORD":
const newWordsClone = [...state.newWords];
// console.log("nwc", newWordsClone);
const seekWord = (wordObject: any) =>
wordObject.word === action.payload.word;
const wordIndex = newWordsClone.findIndex(seekWord);
// console.log("wi", wordIndex, newWordsClone[wordIndex]);
newWordsClone[wordIndex] = action.payload;
return {
...state,
newWords: newWordsClone,
};
case "INCREMENT_ACTIVE_STEP": {
return { ...state, activeStep: state.activeStep + 1 };
}
case "DECREMENT_ACTIVE_STEP": {
return { ...state, activeStep: state.activeStep - 1 };
}
case "RESET_ACTIVE_STEP": {
return { ...state, activeStep: 0 };
}
case "RENDER_NOTIFICATION":
return { ...state, notification: action.payload };
default:
throw new Error();
}
};
const UploadPage = () => {
const [state, dispatch] = useReducer(reducer, initialState); <-- Error
...
}
Respuestas
En su initialState, content.filese establece en una cadena vacía, pero debería estar Fileen su lugar
type Content = {
file: File;
...
};
type InitialState = {
content: Content;
...
};
const initialState = {
content: {
file: "",
},
...
};
Puede solucionarlo inicializando un objeto nulo con el tipo correspondiente
const EMPTY_FILE = Object.freeze(new File([""], "filename"));
const initialState = {
content: {
file: EMPTY_FILE,
},
...
};
También hay un pequeño error en su reductor.
switch (action.type) {
case "SET_FILE":
return { ...state, content: action.payload };
...
}
Debería ser esto
switch (action.type) {
case "SET_FILE":
return { ...state, content: { ...state.content, file: action.payload } };
...
}