So I am confused about industry-standard implementation. I feel this is a hacky way the way I am doing it right now
I want to display an error message whenever there is an actual error and display a failure message whenever the server return a nonsuccess status
The problem here is when there is an actual error on assignUser() it returns the error and this does not trigger the catch of the first function, so it is handled by the else statement instead and shows a failure message while it is an actual error.
I tried to use throw new Error("error) in the catch of assignUser() but the same issue.
The second concern I have is regarding (200 >= status <300) is there a simpler way to check a successful operation other than checking the status which can be 200, 204 ...?
try {
let status = assignUser(user);
if (status >= 200 && status < 300) {
notify.show("message success");
} else {
notify.show("message failure");
}
} catch (e) {
notify.show("message error");
}
export async function assignUser(user) {
try {......
return resp.status;
} catch (e) {
return e;
}
}
I assume assignUser function is making an api call using fetch. So if you are not using the then catch method to resolve the promise, then the assignUser function has to be an async function.
async function assignUser(user) {
try {
const jsonRes = await fetch(url);
if(!jsonRes.ok) {
notify.show("message failure");
} else {
notify.show("message success");
const result = await jsonRes.json();
return result;
}
} catch (e) {
notify.show("message error");
}
}
Here you don't need another function to check the status and all
and instead of checking with the status code you can use the response.ok property.
Hope this helps
Thanks
Related
In JavaScript Try catch block how to retry the same . am facing once scenario any one ca give the best approach to handle this ?
for Example :
const getMyDetails = async()=>{
try{
await getName();
}catch(err){
//But Above FAIL due to some issue
// so I want to try the same again "getName" here until the success - 'not single time'
}
// Second Method for get data
const getName = async()=>{
try{
here am calling API or any kind of subscription But here its failing so am throwing error
}catch(err){
throw new Error(err);
}
getMyDetails()
Note: may be the fail reason like Databse events or some other subscriptions etc..
instead of calling the method name in catch .. what will be the best approach for retry
Thanks in advance
Just Calling Itself If It Fails Will Do The Job
const getMyDetails = async()=>{
try{
await getName();
}catch(err){
getMyDetails()
}
// Second Method for get data
const getName = async()=>{
try{
// Method
}catch(err){
throw new Error(err);
}
getMyDetails()
Here you can see an example behavior and the implementation logic of calling an async function N number of times, only until no errors are thrown.
// We must be inside of an async function to be able to call await
(async function() {
// Example async function which returns the value only if no errors are thrown,
// otherwise calls itself to retry the async call
async function getMyDetails() {
try {
return await getName();
} catch (error) {
return getMyDetails();
}
}
// Example async function which returns value only if the random number is even,
// otherwise throws an Error (simulating an API error response)
async function getName() {
return new Promise((resolve, reject) => {
let randomNumber = Math.floor(Math.random());
if (randomNumber % 2 === 0) {
resolve("Random Name");
}
reject("Example API Error has occured.")
});
}
let myDetails = await getMyDetails();
console.log(myDetails);
})();
I'm trying to exit the function if an error occurs inside the try block, and still run cleanup code in finally.
I'm doing it by using shouldContinue that is set to true initially, and set it to false inside the catch block if the execution shouldn't continue.
async uploadToServer() {
let response;
let shouldContinue = true;
try {
response = await this.uploderService.uploadFileToServer();
} catch (error) {
this.displayUploadError(error);
shouldContinue = false;
} finally {
// run cleanup code anyway
this.resetSession();
}
if (!shouldContinue) {
return;
}
this.saveResponse(response);
// continue execution here
// ...
}
Is there a better way to exit the function after an error occurs inside the try block and still run code in finally?
One way (probably my personal preferred way) is to simply put everything inside the try (if possible - e.g. if nothing else inside the try could throw an unrelated error):
async uploadToServer() {
try {
const response = await this.uploderService.uploadFileToServer();
this.saveResponse(response);
// continue execution here
// ...
} catch (error) {
this.displayUploadError(error);
} finally {
// run cleanup code anyway
this.resetSession();
}
}
Another way is to return in the catch (finally still runs):
async uploadToServer() {
let response;
try {
response = await this.uploderService.uploadFileToServer();
} catch (error) {
this.displayUploadError(error);
return;
} finally {
// run cleanup code anyway
this.resetSession();
}
this.saveResponse(response);
// continue execution here
// ...
}
Finally will be executed anyway, either the try executed or catch.
Check the description in the link below for more information.
Mozilla developer reference
so I have a normal thing you would do to find if a file exists and proceed accordingly:
let response = await fetch(url);
if (response.ok) {
//it exists
} else {
//it doesn't
}
Problem is, of course, if it fails it gives me a TypeError: Failed to fetch and my function stops.
Is there a way I can suppress the error?
I cannot change from a fetch function, i've tried everything else and fetch is the best option in my context.
Thanks in advance.
You will need to implement try and catch and it is quite easy to implement it. You can have a look at Try and Catch Documentation
Have a look at the sample code below
try {
let response = await fetch(url);
}
catch(err) {
alert("Error Message : " + err.message);
}
Is there a way I can suppress the error?
You should wrap your function that may cause the error in try...catch.
const fetch = (isFine) => new Promise(resolve => {
if(isFine)
resolve("Normal data");
else
throw new Error("Error msg...!");
});
const myFunction = async (isFine) => {
try {
const response = await fetch(isFine);
console.log(response);
}
catch(err) {
console.log("Oops..." + err.message);
}
}
myFunction(true);
myFunction(false);
I am not sure if this is right or wrong, but something deep inside me tells me that i am doing it wrong to have logic code on catch stm.
For ex my catch looks something like this:
try{
// do some stuff that throws some unexpected errors
}
catch (error) {
if (error?.graphQLErrors[0]) {
let msg = error.graphQLErrors[0].message
switch (msg) {
case 'limited':
// TODO:: handle
default:
window.location.href = "www.someurl.com";
}
}
Mainly I am thinking that catch stm usually should stay short and clean without logic on it that can cause another error or exception, what happens if the code inside catch throws some error?
It's just fine to have logic in your catch block, if the logic is there in order to handle or report the error. That's what catch blocks are for.
what happens if the code inside catch throws some error?
That's a new error. If you don't catch it, it will propagate to the caller, etc.
Example:
function example() {
try {
// "x" has no method `foo` so this causes an error:
"x".foo();
} catch (e) {
console.log(`Caught error in \`example\`: ${e.message}`);
// "y" has no method `bar` so this causes an error:
"y".bar();
}
}
function wrapper() {
try {
example();
} catch (e) {
console.log(`Caught error in \`wrapper\`: ${e.message}`);
}
}
wrapper();
Throwing errors intentionally from the catch block is a common practice in many places. You can wrap the original into one that can be better handled higher up or perhaps throw a more meaningful error
class MyError extends Error {
constructor(errorCode) {
super();
this.errorCode = errorCode;
}
}
function example() {
try {
// "x" has no method `foo` so this causes an error:
"x".foo();
} catch (e) {
throw new MyError(42);
}
}
function wrapper() {
try {
example();
} catch (e) {
if (e.errorCode === 42) {//specific
console.log(`I know what this error means: the flux capacitor is broken`);
} else {//generic
console.log(`Caught error in \`wrapper\`: ${e.message}`);
}
}
}
wrapper();
can I have logic code if else statements within catch statement?
Yes.
what happens if the code inside catch throws some error?
The error will propagate to the next try catch block.
I have error handling set up using try/catch blocks, which in its simplified form looks like this
try {
// .. Some application logic
try {
// .. some async api code
} catch (e) {
throw new Error("Api Error")
}
return true;
} catch (e) {
throw new Error("Unknown Error")
}
And the issue is, whenever I expect "Api Error" to be returned I get "Unknown Error" it seems like all errors are propagated to the outermost catch?
Is there a way to avoid this or another approach that allows for nested error handling?
In your code, check if exception is happening inside the first try block. If so, the inner try won't be executed.
try {
// .. Some application logic
// exception occurs here
// below code is not executed and the control is given to catch block
try {
//this did not execute
// .. some async api code
} catch (e) {
throw new Error("Api Error")
}
return true;
}
catch (e) {
//control came here
throw new Error("Unknown Error")
}
This is also a possible case:
try {
// .. Some application logic
// no exceptions occur here
// below code is executed
try {
//this did not execute
//exception here
// .. some async api code
} catch (e) {
//control came here and this threw APIerror
throw new Error("Api Error")
}
//this did not execute as the previous catch block raised another exception
return true;
}
catch (e) {
//control came here
throw new Error("Unknown Error")
}
Hope this helps :)