@@ -2449,9 +2449,50 @@ namespace FourSlash {
24492449 Harness . IO . log ( this . spanInfoToString ( this . getNameOrDottedNameSpan ( pos ) ! , "**" ) ) ;
24502450 }
24512451
2452+ private classificationToIdentifier ( classification : number ) {
2453+
2454+ const tokenTypes : string [ ] = [ ] ;
2455+ tokenTypes [ ts . classifier . vscode . TokenType . class ] = 'class' ;
2456+ tokenTypes [ ts . classifier . vscode . TokenType . enum ] = 'enum' ;
2457+ tokenTypes [ ts . classifier . vscode . TokenType . interface ] = 'interface' ;
2458+ tokenTypes [ ts . classifier . vscode . TokenType . namespace ] = 'namespace' ;
2459+ tokenTypes [ ts . classifier . vscode . TokenType . typeParameter ] = 'typeParameter' ;
2460+ tokenTypes [ ts . classifier . vscode . TokenType . type ] = 'type' ;
2461+ tokenTypes [ ts . classifier . vscode . TokenType . parameter ] = 'parameter' ;
2462+ tokenTypes [ ts . classifier . vscode . TokenType . variable ] = 'variable' ;
2463+ tokenTypes [ ts . classifier . vscode . TokenType . enumMember ] = 'enumMember' ;
2464+ tokenTypes [ ts . classifier . vscode . TokenType . property ] = 'property' ;
2465+ tokenTypes [ ts . classifier . vscode . TokenType . function ] = 'function' ;
2466+ tokenTypes [ ts . classifier . vscode . TokenType . member ] = 'member' ;
2467+
2468+ const tokenModifiers : string [ ] = [ ] ;
2469+ tokenModifiers [ ts . classifier . vscode . TokenModifier . async ] = 'async' ;
2470+ tokenModifiers [ ts . classifier . vscode . TokenModifier . declaration ] = 'declaration' ;
2471+ tokenModifiers [ ts . classifier . vscode . TokenModifier . readonly ] = 'readonly' ;
2472+ tokenModifiers [ ts . classifier . vscode . TokenModifier . static ] = 'static' ;
2473+ tokenModifiers [ ts . classifier . vscode . TokenModifier . local ] = 'local' ;
2474+ tokenModifiers [ ts . classifier . vscode . TokenModifier . defaultLibrary ] = 'defaultLibrary' ;
2475+
2476+
2477+ function getTokenTypeFromClassification ( tsClassification : number ) : number | undefined {
2478+ if ( tsClassification > ts . classifier . vscode . TokenEncodingConsts . modifierMask ) {
2479+ return ( tsClassification >> ts . classifier . vscode . TokenEncodingConsts . typeOffset ) - 1 ;
2480+ }
2481+ return undefined ;
2482+ }
2483+
2484+ function getTokenModifierFromClassification ( tsClassification : number ) {
2485+ return tsClassification & ts . classifier . vscode . TokenEncodingConsts . modifierMask ;
2486+ }
2487+
2488+ const typeIdx = getTokenTypeFromClassification ( classification ) || 0 ;
2489+ const modSet = getTokenModifierFromClassification ( classification ) ;
2490+
2491+ const tokenClassifiction = [ tokenTypes [ typeIdx ] , ...tokenModifiers . filter ( ( _ , i ) => modSet & 1 << i ) ] . join ( "." ) ;
2492+ return tokenClassifiction ;
2493+ }
2494+
24522495 private verifyClassifications ( expected : { classificationType : string | number , text ?: string ; textSpan ?: TextSpan } [ ] , actual : ts . ClassifiedSpan [ ] , sourceFileText : string ) {
2453- console . log ( "expected:" , expected ) ;
2454- console . log ( "actual:" , actual ) ;
24552496 if ( actual . length !== expected . length ) {
24562497 this . raiseError ( "verifyClassifications failed - expected total classifications to be " + expected . length +
24572498 ", but was " + actual . length +
@@ -2460,10 +2501,12 @@ namespace FourSlash {
24602501
24612502 ts . zipWith ( expected , actual , ( expectedClassification , actualClassification ) => {
24622503 const expectedType = expectedClassification . classificationType ;
2463- if ( expectedType !== actualClassification . classificationType ) {
2504+ const actualType = typeof actualClassification . classificationType === "number" ? this . classificationToIdentifier ( actualClassification . classificationType ) : actualClassification . classificationType ;
2505+
2506+ if ( expectedType !== actualType ) {
24642507 this . raiseError ( "verifyClassifications failed - expected classifications type to be " +
24652508 expectedType + ", but was " +
2466- actualClassification . classificationType +
2509+ actualType +
24672510 jsonMismatchString ( ) ) ;
24682511 }
24692512
@@ -2514,6 +2557,29 @@ namespace FourSlash {
25142557 }
25152558 }
25162559
2560+ public replaceWithSemanticClassifications ( format : ts . SemanticClassificationFormat . TwentyTwenty ) {
2561+ const actual = this . languageService . getSemanticClassifications ( this . activeFile . fileName ,
2562+ ts . createTextSpan ( 0 , this . activeFile . content . length ) , format ) ;
2563+ const replacement = [ `const c2 = classification("2020");` , `verify.semanticClassificationsAre("2020",` ] ;
2564+ actual . forEach ( a => {
2565+ const identifier = this . classificationToIdentifier ( a . classificationType as number ) ;
2566+ const text = this . activeFile . content . slice ( a . textSpan . start , a . textSpan . start + a . textSpan . length ) ;
2567+ replacement . push ( ` c2.semanticToken("${ identifier } ", "${ text } "), ` ) ;
2568+ } ) ;
2569+ replacement . push ( ");" ) ;
2570+
2571+ throw new Error ( "You need to change the source code of fourslash test to use replaceWithSemanticClassifications" ) ;
2572+
2573+ /**
2574+ const fs = require("fs");
2575+ const testfilePath = this.originalInputFileName.slice(1);
2576+ const testfile = fs.readFileSync(testfilePath, "utf8");
2577+ const newfile = testfile.replace("verify.replaceWithSemanticClassifications(\"2020\")", replacement.join("\n"));
2578+ fs.writeFileSync(testfilePath, newfile);
2579+ */
2580+ }
2581+
2582+
25172583 public verifySemanticClassifications ( format : ts . SemanticClassificationFormat , expected : { classificationType : string | number ; text ?: string } [ ] ) {
25182584 const actual = this . languageService . getSemanticClassifications ( this . activeFile . fileName ,
25192585 ts . createTextSpan ( 0 , this . activeFile . content . length ) , format ) ;
0 commit comments