From a485aab055244b56cd242e7c76d6e3d2ed3927f2 Mon Sep 17 00:00:00 2001 From: Andy Hanson Date: Wed, 27 Jul 2016 07:26:28 -0700 Subject: [PATCH] Lint tests helper files --- Gulpfile.ts | 1 + Jakefile.js | 3 +- tests/perfsys.ts | 53 +++++------ tests/perftsc.ts | 12 +-- tests/webTestServer.ts | 203 +++++++++++++++++++++------------------- tests/webhost/webtsc.ts | 20 ++-- 6 files changed, 150 insertions(+), 142 deletions(-) diff --git a/Gulpfile.ts b/Gulpfile.ts index a070c80da64..6c91ef52cbb 100644 --- a/Gulpfile.ts +++ b/Gulpfile.ts @@ -956,6 +956,7 @@ const lintTargets = [ "src/server/**/*.ts", "scripts/tslint/**/*.ts", "src/services/**/*.ts", + "tests/*.ts", "tests/webhost/*.ts" // Note: does *not* descend recursively ]; diff --git a/Jakefile.js b/Jakefile.js index f63275284d0..174be5e702f 100644 --- a/Jakefile.js +++ b/Jakefile.js @@ -1041,7 +1041,8 @@ var lintTargets = compilerSources .concat(serverCoreSources) .concat(tslintRulesFiles) .concat(servicesSources) - .concat(["Gulpfile.ts"]); + .concat(["Gulpfile.ts"]) + .concat([nodeServerInFile, perftscPath, "tests/perfsys.ts", webhostPath]); desc("Runs tslint on the compiler sources. Optional arguments are: f[iles]=regex"); diff --git a/tests/perfsys.ts b/tests/perfsys.ts index 143d0d637d4..abe09c88a0f 100644 --- a/tests/perfsys.ts +++ b/tests/perfsys.ts @@ -1,8 +1,7 @@ /// /// -module perftest { - +namespace perftest { interface IOLog { resolvePath: ts.Map; fileNames: string[]; @@ -12,20 +11,20 @@ module perftest { getOut(): string; } - export var readFile = ts.sys.readFile; - var writeFile = ts.sys.writeFile; - export var write = ts.sys.write; - var resolvePath = ts.sys.resolvePath; - export var getExecutingFilePath = ts.sys.getExecutingFilePath; - export var getCurrentDirectory = ts.sys.getCurrentDirectory; - var exit = ts.sys.exit; + export const readFile = ts.sys.readFile; + const writeFile = ts.sys.writeFile; + export const write = ts.sys.write; + const resolvePath = ts.sys.resolvePath; + export const getExecutingFilePath = ts.sys.getExecutingFilePath; + export const getCurrentDirectory = ts.sys.getCurrentDirectory; + // const exit = ts.sys.exit; - var args = ts.sys.args; + const args = ts.sys.args; // augment sys so first ts.executeCommandLine call will be finish silently ts.sys.write = (s: string) => { }; ts.sys.exit = (code: number) => { }; - ts.sys.args = [] + ts.sys.args = []; export function restoreSys() { ts.sys.args = args; @@ -44,19 +43,19 @@ module perftest { return args.slice(1); } - var resolvePathLog: ts.Map = {}; - + const resolvePathLog: ts.Map = {}; + export function interceptIO() { ts.sys.resolvePath = (s) => { - var result = resolvePath(s); + const result = resolvePath(s); resolvePathLog[s] = result; return result; }; } export function writeIOLog(fileNames: string[]) { - var path = args[1]; - var log: IOLog = { + const path = args[1]; + const log: IOLog = { fileNames: fileNames, resolvePath: resolvePathLog }; @@ -65,36 +64,36 @@ module perftest { } export function prepare(): IO { - var log = JSON.parse(readFile(args[0])); + const log = JSON.parse(readFile(args[0])); + + const files: ts.Map = {}; + log.fileNames.forEach(f => { files[f] = readFile(f); }); - var files: ts.Map = {}; - log.fileNames.forEach(f => { files[f] = readFile(f); }) - ts.sys.createDirectory = (s: string) => { }; ts.sys.directoryExists = (s: string) => true; ts.sys.fileExists = (s: string) => true; - var currentDirectory = ts.sys.getCurrentDirectory(); + const currentDirectory = ts.sys.getCurrentDirectory(); ts.sys.getCurrentDirectory = () => currentDirectory; - var executingFilePath = ts.sys.getExecutingFilePath(); + const executingFilePath = ts.sys.getExecutingFilePath(); ts.sys.getExecutingFilePath = () => executingFilePath; ts.sys.readFile = (s: string) => { return files[s]; - } + }; ts.sys.resolvePath = (s: string) => { - var path = log.resolvePath[s]; + const path = log.resolvePath[s]; if (!path) { throw new Error("Unexpected path '" + s + "'"); } - return path - } + return path; + }; ts.sys.writeFile = (path: string, data: string) => { }; - var out: string = ""; + let out = ""; ts.sys.write = (s: string) => { out += s; }; diff --git a/tests/perftsc.ts b/tests/perftsc.ts index 89bff1cc006..0753023853e 100644 --- a/tests/perftsc.ts +++ b/tests/perftsc.ts @@ -5,9 +5,9 @@ if (perftest.hasLogIOFlag()) { perftest.interceptIO(); - var compilerHost: ts.CompilerHost = { + const compilerHost: ts.CompilerHost = { getSourceFile: (s, v) => { - var content = perftest.readFile(s); + const content = perftest.readFile(s); return content !== undefined ? ts.createSourceFile(s, content, v) : undefined; }, getDefaultLibFileName: () => ts.combinePaths(ts.getDirectoryPath(ts.normalizePath(perftest.getExecutingFilePath())), "lib.d.ts"), @@ -18,13 +18,13 @@ if (perftest.hasLogIOFlag()) { getNewLine: () => ts.sys.newLine }; - var commandLine = ts.parseCommandLine(perftest.getArgsWithoutLogIOFlag()); - var program = ts.createProgram(commandLine.fileNames, commandLine.options, compilerHost); - var fileNames = program.getSourceFiles().map(f => f.fileName); + const commandLine = ts.parseCommandLine(perftest.getArgsWithoutLogIOFlag()); + const program = ts.createProgram(commandLine.fileNames, commandLine.options, compilerHost); + const fileNames = program.getSourceFiles().map(f => f.fileName); perftest.writeIOLog(fileNames); } else { - var io = perftest.prepare(); + const io = perftest.prepare(); ts.executeCommandLine(perftest.getArgsWithoutIOLogFile()); perftest.write(io.getOut()); } diff --git a/tests/webTestServer.ts b/tests/webTestServer.ts index d9adff05842..ac5f046c1dd 100644 --- a/tests/webTestServer.ts +++ b/tests/webTestServer.ts @@ -9,35 +9,35 @@ import os = require("os"); /// Command line processing /// -if (process.argv[2] == '--help') { - console.log('Runs a node server on port 8888, looking for tests folder in the current directory\n'); - console.log('Syntax: node nodeServer.js [typescriptEnlistmentDirectory] [tests] [--browser] [--verbose]\n'); - console.log('Examples: \n\tnode nodeServer.js .'); - console.log('\tnode nodeServer.js 3000 D:/src/typescript/public --verbose IE'); +if (process.argv[2] == "--help") { + console.log("Runs a node server on port 8888, looking for tests folder in the current directory\n"); + console.log("Syntax: node nodeServer.js [typescriptEnlistmentDirectory] [tests] [--browser] [--verbose]\n"); + console.log("Examples: \n\tnode nodeServer.js ."); + console.log("\tnode nodeServer.js 3000 D:/src/typescript/public --verbose IE"); } function switchToForwardSlashes(path: string) { - return path.replace(/\\/g, "/").replace(/\/\//g, '/'); + return path.replace(/\\/g, "/").replace(/\/\//g, "/"); } -var port = 8888; // harness.ts and webTestResults.html depend on this exact port number. -var rootDir = switchToForwardSlashes(__dirname + '/../'); +const port = 8888; // harness.ts and webTestResults.html depend on this exact port number. -var browser: string; +let browser: string; if (process.argv[2]) { browser = process.argv[2]; - if (browser !== 'chrome' && browser !== 'IE') { - console.log('Invalid command line arguments. Got ' + browser + ' but expected chrome, IE or nothing.'); + if (browser !== "chrome" && browser !== "IE") { + console.log(`Invalid command line arguments. Got ${browser} but expected chrome, IE or nothing.`); } } -var grep = process.argv[3]; +const grep = process.argv[3]; -var verbose = false; -if (process.argv[4] == '--verbose') { +let verbose = false; +if (process.argv[4] == "--verbose") { verbose = true; -} else if (process.argv[4] && process.argv[4] !== '--verbose') { - console.log('Invalid command line arguments. Got ' + process.argv[4] + ' but expected --verbose or nothing.'); +} +else if (process.argv[4] && process.argv[4] !== "--verbose") { + console.log(`Invalid command line arguments. Got ${process.argv[4]} but expected --verbose or nothing.`); } /// Utils /// @@ -48,58 +48,61 @@ function log(msg: string) { } // Copied from the compiler sources -function dir(path: string, spec?: string, options?: any) { +function dir(dirPath: string, spec?: string, options?: any) { options = options || <{ recursive?: boolean; }>{}; + return filesInFolder(dirPath); function filesInFolder(folder: string): string[] { - var folder = switchToForwardSlashes(folder); - var paths: string[] = []; + folder = switchToForwardSlashes(folder); + let paths: string[] = []; // Everything after the current directory is relative - var baseDirectoryLength = process.cwd().length + 1; + const baseDirectoryLength = process.cwd().length + 1; try { - var files = fs.readdirSync(folder); - for (var i = 0; i < files.length; i++) { - var stat = fs.statSync(folder + "/" + files[i]); + const files = fs.readdirSync(folder); + for (let i = 0; i < files.length; i++) { + const stat = fs.statSync(path.join(folder, files[i])); if (options.recursive && stat.isDirectory()) { - paths = paths.concat(filesInFolder(folder + "/" + files[i])); - } else if (stat.isFile() && (!spec || files[i].match(spec))) { - var relativePath = folder.substring(baseDirectoryLength); - paths.push(relativePath + "/" + files[i]); + paths = paths.concat(filesInFolder(path.join(folder, files[i]))); + } + else if (stat.isFile() && (!spec || files[i].match(spec))) { + const relativePath = folder.substring(baseDirectoryLength); + paths.push(path.join(relativePath, files[i])); } } - } catch (err) { + } + catch (err) { // Skip folders that are inaccessible } return paths; } - - return filesInFolder(path); } // fs.rmdirSync won't delete directories with files in it -function deleteFolderRecursive(path: string) { - if (fs.existsSync(path)) { - fs.readdirSync(path).forEach(function (file, index) { - var curPath = path + "/" + file; +function deleteFolderRecursive(dirPath: string) { + if (fs.existsSync(dirPath)) { + fs.readdirSync(dirPath).forEach((file, index) => { + const curPath = path.join(path, file); if (fs.statSync(curPath).isDirectory()) { // recurse deleteFolderRecursive(curPath); - } else { // delete file + } + else { // delete file fs.unlinkSync(curPath); } }); - fs.rmdirSync(path); + fs.rmdirSync(dirPath); } }; function writeFile(path: string, data: any, opts: { recursive: boolean }) { try { fs.writeFileSync(path, data); - } catch (e) { + } + catch (e) { // assume file was written to a directory that exists, if not, start recursively creating them as necessary - var parts = switchToForwardSlashes(path).split('/'); - for (var i = 0; i < parts.length; i++) { - var subDir = parts.slice(0, i).join('/'); + const parts = switchToForwardSlashes(path).split("/"); + for (let i = 0; i < parts.length; i++) { + const subDir = parts.slice(0, i).join("/"); if (!fs.existsSync(subDir)) { fs.mkdir(subDir); } @@ -111,10 +114,10 @@ function writeFile(path: string, data: any, opts: { recursive: boolean }) { /// Request Handling /// function handleResolutionRequest(filePath: string, res: http.ServerResponse) { - var resolvedPath = path.resolve(filePath, ''); - resolvedPath = resolvedPath.substring(resolvedPath.indexOf('tests')); + let resolvedPath = path.resolve(filePath, ""); + resolvedPath = resolvedPath.substring(resolvedPath.indexOf("tests")); resolvedPath = switchToForwardSlashes(resolvedPath); - send('success', res, resolvedPath); + send("success", res, resolvedPath); return; } @@ -123,7 +126,7 @@ function send(result: "success", res: http.ServerResponse, contents: string, con function send(result: "unknown", res: http.ServerResponse, contents: string, contentType?: string): void; function send(result: string, res: http.ServerResponse, contents: string, contentType?: string): void function send(result: string, res: http.ServerResponse, contents: string, contentType = "binary"): void { - var responseCode = result === "success" ? 200 : result === "fail" ? 500 : result === 'unknown' ? 404 : parseInt(result); + const responseCode = result === "success" ? 200 : result === "fail" ? 500 : result === "unknown" ? 404 : parseInt(result); res.writeHead(responseCode, { "Content-Type": contentType }); res.end(contents); return; @@ -131,27 +134,28 @@ function send(result: string, res: http.ServerResponse, contents: string, conten // Reads the data from a post request and passes it to the given callback function processPost(req: http.ServerRequest, res: http.ServerResponse, callback: (data: string) => any): void { - var queryData = ""; - if (typeof callback !== 'function') return null; + let queryData = ""; + if (typeof callback !== "function") return; - if (req.method == 'POST') { - req.on('data', function (data: string) { + if (req.method == "POST") { + req.on("data", (data: string) => { queryData += data; if (queryData.length > 1e8) { queryData = ""; - send("413", res, null); + send("413", res, undefined); console.log("ERROR: destroying connection"); req.connection.destroy(); } }); - req.on('end', function () { - //res.post = url.parse(req.url).query; + req.on("end", () => { + // res.post = url.parse(req.url).query; callback(queryData); }); - } else { - send("405", res, null); + } + else { + send("405", res, undefined); } } @@ -168,108 +172,108 @@ enum RequestType { } function getRequestOperation(req: http.ServerRequest, filename: string) { - if (req.method === 'GET' && req.url.indexOf('?') === -1) { - if (req.url.indexOf('.') !== -1) return RequestType.GetFile; + if (req.method === "GET" && req.url.indexOf("?") === -1) { + if (req.url.indexOf(".") !== -1) return RequestType.GetFile; else return RequestType.GetDir; } else { - var queryData: any = url.parse(req.url, true).query; - if (req.method === 'GET' && queryData.resolve !== undefined) return RequestType.ResolveFile + const queryData: any = url.parse(req.url, /*parseQueryString*/ true).query; + if (req.method === "GET" && queryData.resolve !== undefined) return RequestType.ResolveFile; // mocha uses ?grep= query string as equivalent to the --grep command line option used to filter tests - if (req.method === 'GET' && queryData.grep !== undefined) return RequestType.GetFile - if (req.method === 'POST' && queryData.action) { - var path = req.url.substr(0, req.url.lastIndexOf('?')); - var isFile = path.substring(path.lastIndexOf('/')).indexOf('.') !== -1; + if (req.method === "GET" && queryData.grep !== undefined) return RequestType.GetFile; + if (req.method === "POST" && queryData.action) { + const path = req.url.substr(0, req.url.lastIndexOf("?")); + const isFile = path.substring(path.lastIndexOf("/")).indexOf(".") !== -1; switch (queryData.action.toUpperCase()) { - case 'WRITE': + case "WRITE": return isFile ? RequestType.WriteFile : RequestType.WriteDir; - case 'DELETE': + case "DELETE": return isFile ? RequestType.DeleteFile : RequestType.DeleteDir; - case 'APPEND': + case "APPEND": return isFile ? RequestType.AppendFile : RequestType.Unknown; } } - return RequestType.Unknown + return RequestType.Unknown; } } function handleRequestOperation(req: http.ServerRequest, res: http.ServerResponse, operation: RequestType, reqPath: string) { switch (operation) { case RequestType.GetDir: - var filesInFolder = dir(reqPath, "", { recursive: true }); - send('success', res, filesInFolder.join(',')); + const filesInFolder = dir(reqPath, "", { recursive: true }); + send("success", res, filesInFolder.join(",")); break; case RequestType.GetFile: - fs.readFile(reqPath, function (err, file) { + fs.readFile(reqPath, (err, file) => { const contentType = contentTypeForExtension(path.extname(reqPath)); if (err) { - send('fail', res, err.message, contentType); + send("fail", res, err.message, contentType); } else { - send('success', res, file, contentType); + send("success", res, file, contentType); } }); break; case RequestType.ResolveFile: - var resolveRequest = req.url.match(/(.*)\?resolve/); + const resolveRequest = req.url.match(/(.*)\?resolve/); handleResolutionRequest(resolveRequest[1], res); break; case RequestType.WriteFile: processPost(req, res, (data) => { writeFile(reqPath, data, { recursive: true }); }); - send('success', res, null); + send("success", res, undefined); break; case RequestType.WriteDir: fs.mkdirSync(reqPath); - send('success', res, null); + send("success", res, undefined); break; case RequestType.DeleteFile: if (fs.existsSync(reqPath)) { fs.unlinkSync(reqPath); } - send('success', res, null); + send("success", res, undefined); break; case RequestType.DeleteDir: if (fs.existsSync(reqPath)) { fs.rmdirSync(reqPath); } - send('success', res, null); + send("success", res, undefined); break; case RequestType.AppendFile: processPost(req, res, (data) => { fs.appendFileSync(reqPath, data); }); - send('success', res, null); + send("success", res, undefined); break; case RequestType.Unknown: default: - send('unknown', res, null); + send("unknown", res, undefined); break; } function contentTypeForExtension(ext: string) { switch (ext) { - case '.js': return 'text/javascript'; - case '.css': return 'text/css'; - case '.html': return 'text/html'; - default: return 'binary'; + case ".js": return "text/javascript"; + case ".css": return "text/css"; + case ".html": return "text/html"; + default: return "binary"; } } } -console.log("Static file server running at\n => http://localhost:" + port + "/\nCTRL + C to shutdown"); +console.log(`Static file server running at\n => http://localhost:${port}/\nCTRL + C to shutdown`); -http.createServer(function (req: http.ServerRequest, res: http.ServerResponse) { - log(req.method + ' ' + req.url); - var uri = url.parse(req.url).pathname - var reqPath = path.join(process.cwd(), uri); - var operation = getRequestOperation(req, reqPath); +http.createServer((req: http.ServerRequest, res: http.ServerResponse) => { + log(`${req.method} ${req.url}`); + const uri = url.parse(req.url).pathname; + const reqPath = path.join(process.cwd(), uri); + const operation = getRequestOperation(req, reqPath); handleRequestOperation(req, res, operation, reqPath); }).listen(port); -var browserPath: string; -if ((browser && browser === 'chrome')) { +let browserPath: string; +if (browser === "chrome") { let defaultChromePath = ""; switch (os.platform()) { case "win32": @@ -280,7 +284,7 @@ if ((browser && browser === 'chrome')) { defaultChromePath = "/Applications/Google Chrome.app/Contents/MacOS/Google Chrome"; break; case "linux": - defaultChromePath = "/opt/google/chrome/chrome" + defaultChromePath = "/opt/google/chrome/chrome"; break; default: console.log(`default Chrome location is unknown for platform '${os.platform()}'`); @@ -288,21 +292,24 @@ if ((browser && browser === 'chrome')) { } if (fs.existsSync(defaultChromePath)) { browserPath = defaultChromePath; - } else { + } + else { browserPath = browser; } -} else { - var defaultIEPath = 'C:/Program Files/Internet Explorer/iexplore.exe'; +} +else { + const defaultIEPath = "C:/Program Files/Internet Explorer/iexplore.exe"; if (fs.existsSync(defaultIEPath)) { browserPath = defaultIEPath; - } else { + } + else { browserPath = browser; } } -console.log('Using browser: ' + browserPath); +console.log(`Using browser: ${browserPath}`); -var queryString = grep ? "?grep=" + grep : ''; -child_process.spawn(browserPath, ['http://localhost:' + port + '/tests/webTestResults.html' + queryString], { - stdio: 'inherit' +const queryString = grep ? `?grep=${grep}` : ""; +child_process.spawn(browserPath, [`http://localhost:${port}/tests/webTestResults.html${queryString}`], { + stdio: "inherit" }); diff --git a/tests/webhost/webtsc.ts b/tests/webhost/webtsc.ts index ad3c06c8565..3c682df6274 100644 --- a/tests/webhost/webtsc.ts +++ b/tests/webhost/webtsc.ts @@ -1,17 +1,17 @@ /// -module TypeScript.WebTsc { +namespace TypeScript.WebTsc { declare var RealActiveXObject: { new (s: string): any }; function getWScriptSystem() { - var fso = new RealActiveXObject("Scripting.FileSystemObject"); + const fso = new RealActiveXObject("Scripting.FileSystemObject"); - var fileStream = new ActiveXObject("ADODB.Stream"); + const fileStream = new ActiveXObject("ADODB.Stream"); fileStream.Type = 2 /*text*/; - var args: string[] = []; - for (var i = 0; i < WScript.Arguments.length; i++) { + const args: string[] = []; + for (let i = 0; i < WScript.Arguments.length; i++) { args[i] = WScript.Arguments.Item(i); } return { @@ -37,7 +37,7 @@ module TypeScript.WebTsc { // Load file and read the first two bytes into a string with no interpretation fileStream.Charset = "x-ansi"; fileStream.LoadFromFile(fileName); - var bom = fileStream.ReadText(2) || ""; + const bom = fileStream.ReadText(2) || ""; // Position must be at 0 before encoding can be changed fileStream.Position = 0; // [0xFF,0xFE] and [0xFE,0xFF] mean utf-16 (little or big endian), otherwise default to utf-8 @@ -54,7 +54,7 @@ module TypeScript.WebTsc { } }, writeFile(fileName: string, data: string): boolean { - var f = fso.CreateTextFile(fileName, true); + const f = fso.CreateTextFile(fileName, true); f.Write(data); f.Close(); return true; @@ -90,15 +90,15 @@ module TypeScript.WebTsc { } export function prepareCompiler(currentDir: string, stdOut: ITextWriter, stdErr: ITextWriter) { - var shell = new RealActiveXObject("WScript.Shell"); + const shell = new RealActiveXObject("WScript.Shell"); shell.CurrentDirectory = currentDir; WScript.ScriptFullName = currentDir + "\\tc.js"; WScript.StdOut = stdOut; WScript.StdErr = stdErr; sys = getWScriptSystem(); - return function (commandLine: string) { + return (commandLine: string) => { ts.executeCommandLine(commandLine.split(" ")); - } + }; } }