Error caused by the React component falling into the binding block of unrelated to each other

This is what I came across. Somewhere in the render function of the React component, I have the following:

{first_name} {last_name} 

I replaced it with this:

 {first_name.toUpperCase()} {last_name.toUpperCase()} 

And my application could no longer log in. I use Axios to talk to the backend. Axios is promising. And after I made the changes above. Apparently, he started to execute both the then block and the catch my login API call. When I print the answer in a catch .

 function login(data, success, error) { axios.post('/login', JSON.stringify(data), { baseURL: config.apiUrl, headers: { 'Content-Type': 'application/json; charset=utf-8' } }) .then((response) => success(response.data)) .catch((response) => { console.log(response) error(response.status)}) } 

I get the following:

 TypeError: Cannot read property 'toUpperCase' of undefined 

There is absolutely no connection between the component above (it is a mute component that simply displays material from the props on the page) and the API call code.

This is not the first time I encounter this problem in my application. Has anyone ever encountered anything like this before? I understand that my variables in the component are undefined, and why an error occurs. My question is how does it turn into a promise catch block somewhere on the other end of the application.

+5
source share
2 answers

So, it turns out that in JavaScript, any catch will catch any error that is thrown anywhere in the code. And it is by design.

Here spec :

The throw statement throws a user-defined exception. Execution of the current function will stop (statements after the throw will not be executed), and control will be transferred to the first catch on the call stack. If there is no catch block between the functions of the caller, the program will exit.

One way to solve the problem is to use a handler in all the promises that you enter, that console.log nothing that it did not expect, for example:

 export function apiErrorHandler(handler) { return (error) => { if (error.stack) { throw error } if (error.status && error.data) { handler(error) } else { console.error('Unknown type of error thrown during service request or its handler:', error) } } } 

And how to connect it to the axios service:

 export function serviceGetContacts(success, error) { axios.get(`/contacts`, cfg()) .then((response) => success(response.data)) .catch(apiErrorHandler(error)) } 
+3
source

Your change will raise a TypeError if the first or last name is not already defined. This is pretty similar to completing the login process.

Try using this instead:

 {first_name && first_name.toUpperCase()} {last_name && last_name.toUpperCase()} 
0
source

Source: https://habr.com/ru/post/1242796/


All Articles