Gevorderde probeer / vang / uiteindelik in Javascript en Typescript

Kyk deeglik na die implementering van 'n probeer-vang-uiteindelik-blok

Fouthantering in Javascript & Typescript

Wanneer 'n fout tydens die runtime voorkom, word dit in Javascript en Typescript 'gegooi', soos in die meeste programmeertale die geval is. Onhanteerde foute wat weggegooi word, sal lei tot 'n ongeluk van u program of diens en sodoende tot die slegste gebruikerservaring moontlik. As 'n fout voorkom, gaan enige ongestoorde vordering verlore en kan gebruikers moontlik weer 'n lang proses begin (as 'n gebruiker by 'n platform ingeskryf het deur baie inligting te verskaf). Die gevolg is dat die gebruikers waarskynlik nooit weer u produk sal gebruik nie, want vertroue is verlore.

Om sulke gevalle te hanteer, kan 'n fout 'vasgevang' word. Om foute in Javascript en Typescript vas te lê, draai u u kode eenvoudig in 'n 'probeer'-blok, gevolg deur 'n' vang '-blok.

async function getData(){
  try {
    // Call a dummy async 'fetch'-functoin
    const result = await fetch();
    return { result };
  } catch(error) {
    return { error };
  }
}

// ... later in your code ....

const { result, error } = await getData();

if (error){
  // ... handle error case.
}

// Access the results.

Die gevolg is dat die fout nie deur die hele stelsel versprei nie, wat tot die ongeluk lei, maar direk binne die bestek van u kode hanteer sal word. Die program of diens sal nie crash nie en 'n versagtingstrategie om die fout te verwerk, kan toegepas word.

Spesiale hantering met die "uiteindelik" -blok

As 'n ekstra stap om foute te hanteer, bied Javascript en Typescript 'n bykomende 'laaste' sleutelwoord. So 'n "eindelik" -blok voer enige kode binne sy bestek uit nadat beide die "probeer" -blok sowel as die "vang" -blok uitgevoer is (as daar 'n fout is).

// This function is absolutely save
// to call. It fetches some data and 
// optionally catches a potential error.
//
// After everything's done, a 'finally'
// sends the error to our backend for logs,
// if there was any.
async function getData(){
  // In this case, we store the result
  // and error in mutable variables,
  // then return both.
  let result: Result;
  let error: Error;
  
  try {
    // Call a dummy async 'fetch'-function
    result = await fetch();
  } catch(e) {
    error = e;
  } finally {
    // After the whole try/catch has been
    // processed, we can log the error.
    if(error){
      await trackErrorInCloud(error);
    }
  }
  
  return { result, error };
}

// ... same as before ...

Maar wag, daar is meer! Het u geweet dat die "uiteindelik" -blok uitgevoer word, selfs as u 'n resultaat in die "probeer" - of "vang" -blok lewer? Hier is 'n voorbeeld van wat ek daarmee bedoel.

// Same as the example before, but
// now we directly return from within
// each code block. And this is where
// a side effect can happen.
async function getData(){
  try {
    const result = await fetch();
    return { result };
  } catch(error) {
    return { error }
  } finally {
    //
    // WATCH OUT!
    //
    // Just for demo purpose, but this
    // line of code will override both
    // the return in 'try' as well as 'catch'!
    //
    // Returning inside of 'finally' is therefore
    // dangerous and will lead to hard-to-debug 
    // issues.
    return { finally: true };
  }
}

// data === { finally: true }
const data = await getData();
// Here's a better use case for
// finally.
async function getData(){
  let error: Error;
  
  try {
    const result = await fetch();
    return { result };
  } catch(e) {
    error = e;
    return { error }
  } finally {
    // No return in finally,
    // so it's safe to use.
    if(error){
      await logInCloud()
    }
  }
}

// if no error === { result: ... }
// if error === { error: ... }
const data = await getData();

Opsomming

Soos u gesien het, is die hantering van foute in Javascript en Typescript redelik maklik en vermy 'n volledige crash van u aansoek. Die spesiale hantering van die terugkeer van resultate in die "probeer" - en "vang" -blokke is goed om te weet wanneer u die "eindelik" -blok gebruik, maar moet nie misbruik word om die implementering van u kode in 'n antipatroonstyl te vermy nie.