@@ -807,4 +807,209 @@ namespace ts.projectSystem {
807807 lineText,
808808 } ;
809809 }
810+
811+ export interface GetErrDiagnostics {
812+ file : string | File ;
813+ syntax ?: protocol . Diagnostic [ ] ;
814+ semantic ?: protocol . Diagnostic [ ] ;
815+ suggestion ?: protocol . Diagnostic [ ] ;
816+ }
817+ export interface VerifyGetErrRequestBase {
818+ session : TestSession ;
819+ host : TestServerHost ;
820+ onErrEvent ?: ( ) => void ;
821+ existingTimeouts ?: number ;
822+ }
823+ export interface VerifyGetErrRequest extends VerifyGetErrRequestBase {
824+ expected : readonly GetErrDiagnostics [ ] ;
825+ }
826+ export function verifyGetErrRequest ( request : VerifyGetErrRequest ) {
827+ const { session, expected } = request ;
828+ session . clearMessages ( ) ;
829+ const expectedSequenceId = session . getNextSeq ( ) ;
830+ session . executeCommandSeq < protocol . GeterrRequest > ( {
831+ command : protocol . CommandTypes . Geterr ,
832+ arguments : {
833+ delay : 0 ,
834+ files : expected . map ( f => filePath ( f . file ) )
835+ }
836+ } ) ;
837+ checkAllErrors ( { ...request , expectedSequenceId } ) ;
838+ }
839+
840+ export interface CheckAllErrors extends VerifyGetErrRequest {
841+ expectedSequenceId : number ;
842+ }
843+ function checkAllErrors ( { expected, expectedSequenceId, ...rest } : CheckAllErrors ) {
844+ for ( let i = 0 ; i < expected . length ; i ++ ) {
845+ checkErrorsInFile ( {
846+ ...rest ,
847+ expected : expected [ i ] ,
848+ expectedSequenceId : i === expected . length - 1 ? expectedSequenceId : undefined ,
849+ } ) ;
850+ }
851+ }
852+
853+ function filePath ( file : string | File ) {
854+ return isString ( file ) ? file : file . path ;
855+ }
856+ interface CheckErrorsInFile extends VerifyGetErrRequestBase {
857+ expected : GetErrDiagnostics ;
858+ expectedSequenceId ?: number ;
859+ }
860+ function checkErrorsInFile ( {
861+ session, host, onErrEvent, existingTimeouts, expectedSequenceId,
862+ expected : { file, syntax, semantic, suggestion } ,
863+ } : CheckErrorsInFile ) {
864+ onErrEvent = onErrEvent || noop ;
865+ if ( existingTimeouts !== undefined ) {
866+ host . checkTimeoutQueueLength ( existingTimeouts + 1 ) ;
867+ host . runQueuedTimeoutCallbacks ( host . getNextTimeoutId ( ) - 1 ) ;
868+ }
869+ else {
870+ host . checkTimeoutQueueLengthAndRun ( 1 ) ;
871+ }
872+ if ( syntax ) {
873+ onErrEvent ( ) ;
874+ checkErrorMessage ( session , "syntaxDiag" , { file : filePath ( file ) , diagnostics : syntax } ) ;
875+ }
876+ if ( semantic ) {
877+ session . clearMessages ( ) ;
878+
879+ host . runQueuedImmediateCallbacks ( 1 ) ;
880+ onErrEvent ( ) ;
881+ checkErrorMessage ( session , "semanticDiag" , { file : filePath ( file ) , diagnostics : semantic } ) ;
882+ }
883+ if ( suggestion ) {
884+ session . clearMessages ( ) ;
885+
886+ host . runQueuedImmediateCallbacks ( 1 ) ;
887+ onErrEvent ( ) ;
888+ checkErrorMessage ( session , "suggestionDiag" , { file : filePath ( file ) , diagnostics : suggestion } ) ;
889+ }
890+ if ( expectedSequenceId !== undefined ) {
891+ checkCompleteEvent ( session , syntax || semantic || suggestion ? 2 : 1 , expectedSequenceId ) ;
892+ }
893+ session . clearMessages ( ) ;
894+ }
895+
896+ function verifyErrorsUsingGeterr ( { allFiles, openFiles, expectedGetErr } : VerifyGetErrScenario ) {
897+ it ( "verifies the errors in open file" , ( ) => {
898+ const host = createServerHost ( [ ...allFiles ( ) , libFile ] ) ;
899+ const session = createSession ( host , { canUseEvents : true , } ) ;
900+ openFilesForSession ( openFiles ( ) , session ) ;
901+
902+ verifyGetErrRequest ( { session, host, expected : expectedGetErr ( ) } ) ;
903+ } ) ;
904+ }
905+
906+ function verifyErrorsUsingGeterrForProject ( { allFiles, openFiles, expectedGetErrForProject } : VerifyGetErrScenario ) {
907+ it ( "verifies the errors in projects" , ( ) => {
908+ const host = createServerHost ( [ ...allFiles ( ) , libFile ] ) ;
909+ const session = createSession ( host , { canUseEvents : true , } ) ;
910+ openFilesForSession ( openFiles ( ) , session ) ;
911+
912+ session . clearMessages ( ) ;
913+ for ( const expected of expectedGetErrForProject ( ) ) {
914+ const expectedSequenceId = session . getNextSeq ( ) ;
915+ session . executeCommandSeq < protocol . GeterrForProjectRequest > ( {
916+ command : protocol . CommandTypes . GeterrForProject ,
917+ arguments : {
918+ delay : 0 ,
919+ file : expected . project
920+ }
921+ } ) ;
922+
923+ checkAllErrors ( { session, host, expected : expected . errors , expectedSequenceId } ) ;
924+ }
925+ } ) ;
926+ }
927+
928+ function verifyErrorsUsingSyncMethods ( { allFiles, openFiles, expectedSyncDiagnostics } : VerifyGetErrScenario ) {
929+ it ( "verifies the errors using sync commands" , ( ) => {
930+ const host = createServerHost ( [ ...allFiles ( ) , libFile ] ) ;
931+ const session = createSession ( host ) ;
932+ openFilesForSession ( openFiles ( ) , session ) ;
933+ for ( const { file, project, syntax, semantic, suggestion } of expectedSyncDiagnostics ( ) ) {
934+ const actualSyntax = session . executeCommandSeq < protocol . SyntacticDiagnosticsSyncRequest > ( {
935+ command : protocol . CommandTypes . SyntacticDiagnosticsSync ,
936+ arguments : {
937+ file : filePath ( file ) ,
938+ projectFileName : project
939+ }
940+ } ) . response as protocol . Diagnostic [ ] ;
941+ assert . deepEqual ( actualSyntax , syntax , `Syntax diagnostics for file: ${ filePath ( file ) } , project: ${ project } ` ) ;
942+ const actualSemantic = session . executeCommandSeq < protocol . SemanticDiagnosticsSyncRequest > ( {
943+ command : protocol . CommandTypes . SemanticDiagnosticsSync ,
944+ arguments : {
945+ file : filePath ( file ) ,
946+ projectFileName : project
947+ }
948+ } ) . response as protocol . Diagnostic [ ] ;
949+ assert . deepEqual ( actualSemantic , semantic , `Semantic diagnostics for file: ${ filePath ( file ) } , project: ${ project } ` ) ;
950+ const actualSuggestion = session . executeCommandSeq < protocol . SuggestionDiagnosticsSyncRequest > ( {
951+ command : protocol . CommandTypes . SuggestionDiagnosticsSync ,
952+ arguments : {
953+ file : filePath ( file ) ,
954+ projectFileName : project
955+ }
956+ } ) . response as protocol . Diagnostic [ ] ;
957+ assert . deepEqual ( actualSuggestion , suggestion , `Suggestion diagnostics for file: ${ filePath ( file ) } , project: ${ project } ` ) ;
958+ }
959+ } ) ;
960+ }
961+
962+ function verifyConfigFileErrors ( { allFiles, openFiles, expectedConfigFileDiagEvents } : VerifyGetErrScenario ) {
963+ it ( "verify config file errors" , ( ) => {
964+ const host = createServerHost ( [ ...allFiles ( ) , libFile ] ) ;
965+ const { session, events } = createSessionWithEventTracking < server . ConfigFileDiagEvent > ( host , server . ConfigFileDiagEvent ) ;
966+
967+ for ( const file of openFiles ( ) ) {
968+ session . executeCommandSeq < protocol . OpenRequest > ( {
969+ command : protocol . CommandTypes . Open ,
970+ arguments : { file : file . path }
971+ } ) ;
972+ }
973+
974+ assert . deepEqual ( events , expectedConfigFileDiagEvents ( ) . map ( data => ( {
975+ eventName : server . ConfigFileDiagEvent ,
976+ data
977+ } ) ) ) ;
978+ } ) ;
979+ }
980+
981+ export interface GetErrForProjectDiagnostics {
982+ project : string ;
983+ errors : readonly GetErrDiagnostics [ ] ;
984+ }
985+ export interface SyncDiagnostics extends GetErrDiagnostics {
986+ project ?: string ;
987+ }
988+ export interface VerifyGetErrScenario {
989+ allFiles : ( ) => readonly File [ ] ;
990+ openFiles : ( ) => readonly File [ ] ;
991+ expectedGetErr : ( ) => readonly GetErrDiagnostics [ ] ;
992+ expectedGetErrForProject : ( ) => readonly GetErrForProjectDiagnostics [ ] ;
993+ expectedSyncDiagnostics : ( ) => readonly SyncDiagnostics [ ] ;
994+ expectedConfigFileDiagEvents : ( ) => readonly server . ConfigFileDiagEvent [ "data" ] [ ] ;
995+ }
996+ export function verifyGetErrScenario ( scenario : VerifyGetErrScenario ) {
997+ verifyErrorsUsingGeterr ( scenario ) ;
998+ verifyErrorsUsingGeterrForProject ( scenario ) ;
999+ verifyErrorsUsingSyncMethods ( scenario ) ;
1000+ verifyConfigFileErrors ( scenario ) ;
1001+ }
1002+
1003+ export function emptyDiagnostics ( file : File ) : GetErrDiagnostics {
1004+ return {
1005+ file,
1006+ syntax : emptyArray ,
1007+ semantic : emptyArray ,
1008+ suggestion : emptyArray
1009+ } ;
1010+ }
1011+
1012+ export function syncDiagnostics ( diagnostics : GetErrDiagnostics , project : string ) : SyncDiagnostics {
1013+ return { project, ...diagnostics } ;
1014+ }
8101015}
0 commit comments