Adds support for `styleUrls` definitions in the same way `templateUrl` definitions are provided; clicking on styleUrl will take a user to the respective file. Unifies some code in determining a URL definition. We first check if a url is a `templateUrl`; if it's not, we check that it's a `styleUrl` or return no definitions. PR Close #32464
		
			
				
	
	
		
			204 lines
		
	
	
		
			6.2 KiB
		
	
	
	
		
			TypeScript
		
	
	
	
	
	
			
		
		
	
	
			204 lines
		
	
	
		
			6.2 KiB
		
	
	
	
		
			TypeScript
		
	
	
	
	
	
| import {ChildProcess, fork} from 'child_process';
 | |
| import {join} from 'path';
 | |
| import {goldenMatcher} from './matcher';
 | |
| import {Client} from './tsclient';
 | |
| 
 | |
| describe('Angular Language Service', () => {
 | |
|   jasmine.DEFAULT_TIMEOUT_INTERVAL = 10000; /* 10 seconds */
 | |
|   const PWD = process.env.PWD!;
 | |
|   const SERVER_PATH = './node_modules/typescript/lib/tsserver.js';
 | |
|   let server: ChildProcess;
 | |
|   let client: Client;
 | |
| 
 | |
|   beforeEach(() => {
 | |
|     jasmine.addMatchers(goldenMatcher);
 | |
|     server = fork(
 | |
|         SERVER_PATH,
 | |
|         [
 | |
|           '--logVerbosity',
 | |
|           'verbose',
 | |
|           '--logFile',
 | |
|           join(PWD, 'tsserver.log'),
 | |
|         ],
 | |
|         {
 | |
|           stdio: ['pipe', 'pipe', 'inherit', 'ipc'],
 | |
|         });
 | |
|     client = new Client(server);
 | |
|     client.listen();
 | |
|   });
 | |
| 
 | |
|   afterEach(async () => {
 | |
|     client.sendRequest('exit', {});
 | |
| 
 | |
|     // Give server process some time to flush all messages
 | |
|     await new Promise((resolve) => setTimeout(resolve, 1000));
 | |
|   });
 | |
| 
 | |
|   it('should be launched as tsserver plugin', async () => {
 | |
|     let response = await client.sendRequest('configure', {
 | |
|       hostInfo: 'vscode',
 | |
|     });
 | |
|     expect(response).toMatchGolden('configure.json');
 | |
|     response = await client.sendRequest('compilerOptionsForInferredProjects', {
 | |
|       'options': {
 | |
|         module: 'CommonJS',
 | |
|         target: 'ES6',
 | |
|         allowSyntheticDefaultImports: true,
 | |
|         allowNonTsExtensions: true,
 | |
|         allowJs: true,
 | |
|         jsx: 'Preserve'
 | |
|       }
 | |
|     });
 | |
|     expect(response).toMatchGolden('compilerOptionsForInferredProjects.json');
 | |
|     // Server does not send response to open request
 | |
|     // https://github.com/Microsoft/TypeScript/blob/master/lib/protocol.d.ts#L1055
 | |
|     client.sendRequest('open', {
 | |
|       file: `${PWD}/project/app/app.module.ts`,
 | |
|     });
 | |
|     // Server does not send response to geterr request
 | |
|     // https://github.com/Microsoft/TypeScript/blob/master/lib/protocol.d.ts#L1770
 | |
|     client.sendRequest('geterr', {delay: 0, files: [`${PWD}/project/app/app.module.ts`]});
 | |
|   });
 | |
| 
 | |
|   it('should perform completions', async () => {
 | |
|     await client.sendRequest('configure', {
 | |
|       hostInfo: 'vscode',
 | |
|     });
 | |
|     await client.sendRequest('compilerOptionsForInferredProjects', {
 | |
|       'options': {
 | |
|         module: 'CommonJS',
 | |
|         target: 'ES6',
 | |
|         allowSyntheticDefaultImports: true,
 | |
|         allowNonTsExtensions: true,
 | |
|         allowJs: true,
 | |
|         jsx: 'Preserve'
 | |
|       }
 | |
|     });
 | |
| 
 | |
|     client.sendRequest('open', {
 | |
|       file: `${PWD}/project/app/app.component.ts`,
 | |
|     });
 | |
| 
 | |
|     client.sendRequest('geterr', {delay: 0, files: [`${PWD}/project/app/app.component.ts`]});
 | |
| 
 | |
|     client.sendRequest('change', {
 | |
|       file: `${PWD}/project/app/app.component.ts`,
 | |
|       line: 5,
 | |
|       offset: 30,
 | |
|       endLine: 5,
 | |
|       endOffset: 30,
 | |
|       insertString: '.',
 | |
|     });
 | |
| 
 | |
|     const response = await client.sendRequest('completionInfo', {
 | |
|       file: `${PWD}/project/app/app.component.ts`,
 | |
|       line: 5,
 | |
|       offset: 31,
 | |
|     });
 | |
|     expect(response).toMatchGolden('completionInfo.json');
 | |
|   });
 | |
| 
 | |
|   it('should perform quickinfo', async () => {
 | |
|     client.sendRequest('open', {
 | |
|       file: `${PWD}/project/app/app.component.ts`,
 | |
|     });
 | |
| 
 | |
|     const resp1 = await client.sendRequest('reload', {
 | |
|       file: `${PWD}/project/app/app.component.ts`,
 | |
|       tmpFile: `${PWD}/project/app/app.component.ts`,
 | |
|     }) as any;
 | |
|     expect(resp1.command).toBe('reload');
 | |
|     expect(resp1.success).toBe(true);
 | |
| 
 | |
|     const resp2 = await client.sendRequest('quickinfo', {
 | |
|       file: `${PWD}/project/app/app.component.ts`,
 | |
|       line: 5,
 | |
|       offset: 28,
 | |
|     });
 | |
|     expect(resp2).toMatchGolden('quickinfo.json');
 | |
|   });
 | |
| 
 | |
|   it('should perform definition', async () => {
 | |
|     client.sendRequest('open', {
 | |
|       file: `${PWD}/project/app/app.component.ts`,
 | |
|     });
 | |
| 
 | |
|     const resp1 = await client.sendRequest('reload', {
 | |
|       file: `${PWD}/project/app/app.component.ts`,
 | |
|       tmpFile: `${PWD}/project/app/app.component.ts`,
 | |
|     }) as any;
 | |
|     expect(resp1.command).toBe('reload');
 | |
|     expect(resp1.success).toBe(true);
 | |
| 
 | |
|     const resp2 = await client.sendRequest('definition', {
 | |
|       file: `${PWD}/project/app/app.component.ts`,
 | |
|       line: 5,
 | |
|       offset: 28,
 | |
|     });
 | |
|     expect(resp2).toMatchGolden('definition.json');
 | |
|   });
 | |
| 
 | |
|   it('should perform definitionAndBoundSpan', async () => {
 | |
|     client.sendRequest('open', {
 | |
|       file: `${PWD}/project/app/app.component.ts`,
 | |
|     });
 | |
| 
 | |
|     const resp1 = await client.sendRequest('reload', {
 | |
|       file: `${PWD}/project/app/app.component.ts`,
 | |
|       tmpFile: `${PWD}/project/app/app.component.ts`,
 | |
|     }) as any;
 | |
|     expect(resp1.command).toBe('reload');
 | |
|     expect(resp1.success).toBe(true);
 | |
| 
 | |
|     const resp2 = await client.sendRequest('definitionAndBoundSpan', {
 | |
|       file: `${PWD}/project/app/app.component.ts`,
 | |
|       line: 5,
 | |
|       offset: 28,
 | |
|     });
 | |
|     expect(resp2).toMatchGolden('definitionAndBoundSpan.json');
 | |
|   });
 | |
| 
 | |
|   it('should perform definitionAndBoundSpan for template URLs', async () => {
 | |
|     client.sendRequest('open', {
 | |
|       file: `${PWD}/project/app/widget.component.ts`,
 | |
|     });
 | |
| 
 | |
|     const resp1 = await client.sendRequest('reload', {
 | |
|       file: `${PWD}/project/app/widget.component.ts`,
 | |
|       tmpFile: `${PWD}/project/app/widget.component.ts`,
 | |
|     }) as any;
 | |
|     expect(resp1.command).toBe('reload');
 | |
|     expect(resp1.success).toBe(true);
 | |
| 
 | |
|     const resp2 = await client.sendRequest('definitionAndBoundSpan', {
 | |
|       file: `${PWD}/project/app/widget.component.ts`,
 | |
|       line: 5,
 | |
|       offset: 19,
 | |
|     });
 | |
|     expect(resp2).toMatchGolden('templateUrlDefinition.json');
 | |
|   });
 | |
| 
 | |
|   it('should perform definitionAndBoundSpan for style URLs', async () => {
 | |
|     client.sendRequest('open', {
 | |
|       file: `${PWD}/project/app/widget.component.ts`,
 | |
|     });
 | |
|     client.sendRequest('open', {
 | |
|       file: `${PWD}/project/app/style.css`,
 | |
|     });
 | |
| 
 | |
|     const resp1 = await client.sendRequest('reload', {
 | |
|       file: `${PWD}/project/app/widget.component.ts`,
 | |
|       tmpFile: `${PWD}/project/app/widget.component.ts`,
 | |
|     }) as any;
 | |
|     expect(resp1.command).toBe('reload');
 | |
|     expect(resp1.success).toBe(true);
 | |
| 
 | |
|     const resp2 = await client.sendRequest('definitionAndBoundSpan', {
 | |
|       file: `${PWD}/project/app/widget.component.ts`,
 | |
|       line: 6,
 | |
|       offset: 18,
 | |
|     });
 | |
|     expect(resp2).toMatchGolden('styleUrlsDefinition.json');
 | |
|   });
 | |
| });
 |