9

Heyo,

I have a following function

async function fnIsOnScreenOnce(img, desc,iCounter,client,repeatDelay=0) {
  await timeout(repeatDelay);
  let screenshot= await client.screenshot()

  let buf = new Buffer(screenshot.value, 'base64');
  let img1 = cv.imdecode(buf)
  let result = img1.matchTemplate(img, 5).minMaxLoc(); 
  result.screenshot=img1;
  if (result.maxVal <= 0.65) {
      // Fail
      const msg = "Can't see object yet";
      throw new Error(result);
  }
        // All good
        console.log("result:"+result)
        logger.info("Found image on screen: "+desc);
        return result;
}

Call of the function

function fnIsOnScreen(img,client, repeats = 5, desc, wait = 2000,repeatDelay) {
    logger.info("Looking for image on screen:" +desc +" with " + repeats + " repeats ");
    let iCounter = 0;
    let init = ()=> timeout(wait).then((asd)=>{
      const attempt = () => fnIsOnScreenOnce(img, desc, iCounter,client,repeatDelay).then((data=>{
        let imagepath=fnMarkOnImage(data.screenshot,img,data,outputDir)
        let description={};
        description.action="Is image on screen ?";
        description.desc=desc;
        description.repeats=repeats;
        description.wait=wait;
        description.img=imagepath;
        description.message="is this correct element ? if is then it was found correctly";
        fnPushToOutputArray(description)
      return data;
      })).catch(err => {
              console.log(JSON.stringify(err));
              console.log(err);
              console.log(err.result);
              iCounter++;
              if (iCounter === repeats) {
                  // Failed, out of retries
                  logger.info("Object not found : " + desc);
                  return Promise.reject("Object not found : " + desc);
              }
              // Retry after waiting
              return attempt();
          });
          return attempt();      
    })
    return init();


}

result object contains some date. On error result contains {} object with no values in it. I would need to get all the values. So how can i pass result object through throw new error to retrieve it in catch ?

5
  • "on error" Why are you throwing an error? Why aren't you just returning that the value isn't high enough? Commented Mar 12, 2018 at 13:16
  • I am throwing an error because I repeat this function until it reachs its limit. I repeat it by calling it again in catch block. I check as well in catch block if it reached the limit. If it does i need to save result even if its erroneous one Commented Mar 12, 2018 at 13:18
  • Can you add the catch block Commented Mar 12, 2018 at 13:21
  • @Stamos you have it there Commented Mar 12, 2018 at 13:22
  • The .catch method you are using is designed to invoke upon the Promise Object's reject - ie. when the Promise is not resolved. This is different than a standard try/catch. Commented Mar 12, 2018 at 13:29

3 Answers 3

11

One way to return extra data with error is to extend Error class and add them your self

class MyError extends Error {

    constructor(message, errorExtraParams) {
        super(message);
        this._errorExtraParams = errorExtraParams;
    }

    get errorExtraParams() {

        return this._errorExtraParams;

    }

}

throw new MyError("Error!!!", {})
//or
let mError =  new MyError("Error!!!", {})
console.log(mError.errorExtraParams)

But I suggest you don't use throw Error, because I don't like to throw Errors for insignificant reasons. What I mean is that in your case there is no reason to throw error cause there is no error and no reason to create an error just to tell you code "Hey I didnt find the image" instead just return false.

async function fnIsOnScreenOnce(img, desc, iCounter, client, repeatDelay = 0) {
    await timeout(repeatDelay);
    let screenshot = await client.screenshot()

    let buf = new Buffer(screenshot.value, 'base64');
    let img1 = cv.imdecode(buf)
    let result = img1.matchTemplate(img, 5).minMaxLoc();
    result.screenshot = img1;
    if (result.maxVal <= 0.65) {
        const msg = "Can't see object yet";
        return false;
    }
    // All good
    console.log("result:" + result)
    logger.info("Found image on screen: " + desc);
    return result;
}

function fnIsOnScreen(img, client, repeats = 5, desc, wait = 2000, repeatDelay) {
    logger.info("Looking for image on screen:" + desc + " with " + repeats + " repeats ");
    let iCounter = 0;
    let init = () => timeout(wait).then((asd) => {

        let found = false;
        do {
            let found = await fnIsOnScreenOnce(img, desc, iCounter, client, repeatDelay)
        } while (found !== false && iCounter++ < 10)

        let imagepath = fnMarkOnImage(found.screenshot, img, found, outputDir)

        let description = {};
        description.action = "Is image on screen ?";
        description.desc = desc;
        description.repeats = repeats;
        description.wait = wait;
        description.img = imagepath;
        description.message = "is this correct element ? if is then it was found correctly";
        fnPushToOutputArray(description)

        return found;

    })
    return init();
}
Sign up to request clarification or add additional context in comments.

Comments

4

You should pass a String to the Error Object, so if you want to exchange an object you could use JSON.stringify() like this:

try {
  throw new Error(JSON.stringify({result:"Hello, World"}));
}
catch(error) {
  console.log(JSON.parse(error.message))
}

As you can see, this is how you would send data from a try to a catch through throwing errors. You can ofc make the second part in the catch way shorter:

error = JSON.parse(error.message);

4 Comments

Yeah I was thinkin about this solution but its kinda dirty one :D Thx anway I ll mark if nobody else will come up with better one
you can access error massing by saying error.message :) no need to to cut it
and no need for the toString then ^^
sorry @Luca the guy under you got a correct solution
3

You can try an approach like this

try {
   const err = new Error("My Error Occurred");
   err.extra ='Extra details';
   throw err;
}
catch (error) {
    console.log(error.extra)
}

As Error itself is an Object ,We can make use of this to pass extra variables of our choice

Comments

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.