2

The Typescript compiler APIs allow for programmatic creation of watch compilers through the use of the ts.createWatchCompilerHost API, with an example of it's use demonstrated in the Typescript docs here.

This API accepts a callback as its last argument that will be called anytime the watch status changes, with a Diagnostic object provided that describes the change in the watch status.

Using these diagnostic events, I'm attempting to discern between a compiling, success, and failure state. I've got detection of compiling state working fine, but I've come across an oddity when determining the difference between success and failure.

The trouble I'm having is due to the fact that the diagnostic codes are applied as follows. If there was 1 error while building, code 6193 is provided, otherwise code 6194 is provided. This means that code 6194 is provided if there were no errors (a success) or if there were 2+ errors (a failure). You can see this logic in the ts compiler here.

What is the expected way for a user of createWatchCompilerHost to determine between the case of no errors on build and the case of 1+ errors on build?

A hacky solution is to parse the diagnostic.messageText to check for Found 0 errors. but that seems extremely fragile and is a solution I would prefer to avoid.

2
  • It's very strange it has the same diagnostic code for 0 errors and 2+ errors. The code in the compiler doesn't look correct to me, but it's done a few times so maybe it is correct. You may want to open an issue in the typescript repo about this to see what they say. Commented Jul 24, 2019 at 14:05
  • 1
    In case anyone gets here wondering the same thing, I've opened up an issue against the typescript repo on github: Issue Link. Commented Jul 24, 2019 at 22:31

1 Answer 1

1

TS 3.7

In TypeScript 3.7 there is now an errorCount parameter on reportWatchStatusChanged:

function reportWatchStatusChanged(
    diagnostic: Diagnostic,
    newLine: string,
    options: CompilerOptions,
    // I'm not sure why this is nullable, I am asking in the issue
    errorCount?: number
) {
    // check error count here
}

Pre-TS 3.7

Given the following watch host from the example:

const host = ts.createWatchCompilerHost(
  configPath,
  {},
  ts.sys,
  createProgram,
  reportDiagnostic,
  reportWatchStatusChanged
);

You could add a flag that's triggered by the reportDiagnostic callback and then check and reset that flag in reportWatchStatusChanged.

For example:

let hadDiagnostics = false;

function reportDiagnostic(diagnostic: ts.Diagnostic) {
  hadDiagnostics = true;
  // ...etc...
}

function reportWatchStatusChanged(diagnostic: ts.Diagnostic) {
  if (hadDiagnostics) {
      console.log("Failed.");
      hadDiagnostics = false;
  } else {
      console.log("Success.");
  }

  // ...etc...
}
Sign up to request clarification or add additional context in comments.

3 Comments

I thought about this, but my only worry was if there was some type of reported Diagnostic that didn't actually represent a real error. Is every Diagnostic passed to reportDiagnostic representing some actual error?
@casieber yes. I just took a look through the source to confirm and they will all be actual errors (see how reportDiagnostic is called here). As you mentioned in the question though, it would be nice if the diagnostic code were different for a success vs a failure with 2+ errors.
Got it. Thanks. I'll go ahead and mark this as the answer and check with the TS team about getting something to differentiate.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.