Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Adds tsc --init option #4037

Merged
merged 9 commits into from
Aug 26, 2015
Merged
Show file tree
Hide file tree
Changes from 4 commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
20 changes: 11 additions & 9 deletions Jakefile.js
Original file line number Diff line number Diff line change
Expand Up @@ -141,7 +141,9 @@ var harnessSources = harnessCoreSources.concat([
"session.ts",
"versionCache.ts",
"convertToBase64.ts",
"transpile.ts"
"transpile.ts",
"projectInit.ts",
"jsonWithCommentsAndTrailingCommas.ts"
].map(function (f) {
return path.join(unittestsDirectory, f);
})).concat([
Expand Down Expand Up @@ -339,10 +341,10 @@ file(diagnosticInfoMapTs, [processDiagnosticMessagesJs, diagnosticMessagesJson],
complete();
});
ex.run();
}, {async: true});
}, {async: true});

desc("Generates a diagnostic file in TypeScript based on an input JSON file");
task("generate-diagnostics", [diagnosticInfoMapTs]);
task("generate-diagnostics", [diagnosticInfoMapTs]);


// Publish nightly
Expand Down Expand Up @@ -479,11 +481,11 @@ file(specMd, [word2mdJs, specWord], function () {
child_process.exec(cmd, function () {
complete();
});
}, {async: true});
}, {async: true});


desc("Generates a Markdown version of the Language Specification");
task("generate-spec", [specMd]);
task("generate-spec", [specMd]);


// Makes a new LKG. This target does not build anything, but errors if not all the outputs are present in the built/local directory
Expand Down Expand Up @@ -615,7 +617,7 @@ task("runtests", ["tests", builtLocalDirectory], function() {
exec(cmd, deleteTemporaryProjectOutput);
}, {async: true});

desc("Generates code coverage data via instanbul");
desc("Generates code coverage data via instanbul");
task("generate-code-coverage", ["tests", builtLocalDirectory], function () {
var cmd = 'istanbul cover node_modules/mocha/bin/_mocha -- -R min -t ' + testTimeout + ' ' + run;
console.log(cmd);
Expand Down Expand Up @@ -658,7 +660,7 @@ task("runtests-browser", ["tests", "browserify", builtLocalDirectory], function(
function getDiffTool() {
var program = process.env['DIFF']
if (!program) {
fail("Add the 'DIFF' environment variable to the path of the program you want to use.");
fail("Add the 'DIFF' environment variable to the path of the program you want to use.");
}
return program;
}
Expand All @@ -667,14 +669,14 @@ function getDiffTool() {
desc("Diffs the compiler baselines using the diff tool specified by the 'DIFF' environment variable");
task('diff', function () {
var cmd = '"' + getDiffTool() + '" ' + refBaseline + ' ' + localBaseline;
console.log(cmd);
console.log(cmd);
exec(cmd);
}, {async: true});

desc("Diffs the RWC baselines using the diff tool specified by the 'DIFF' environment variable");
task('diff-rwc', function () {
var cmd = '"' + getDiffTool() + '" ' + refRwcBaseline + ' ' + localRwcBaseline;
console.log(cmd);
console.log(cmd);
exec(cmd);
}, {async: true});

Expand Down
138 changes: 131 additions & 7 deletions src/compiler/commandLineParser.ts
Original file line number Diff line number Diff line change
Expand Up @@ -30,6 +30,11 @@ namespace ts {
type: "boolean",
description: Diagnostics.Print_this_message,
},
{
name: "init",
type: "boolean",
description: Diagnostics.Initializes_a_TypeScript_project_and_creates_a_tsconfig_json_file,
},
{
name: "inlineSourceMap",
type: "boolean",
Expand Down Expand Up @@ -221,19 +226,36 @@ namespace ts {
}
];

export function parseCommandLine(commandLine: string[]): ParsedCommandLine {
let options: CompilerOptions = {};
let fileNames: string[] = [];
let errors: Diagnostic[] = [];
let shortOptionNames: Map<string> = {};
let optionNameMap: Map<CommandLineOption> = {};
export interface OptionNameMap {
optionNameMap: Map<CommandLineOption>;
shortOptionNames: Map<string>;
}

let optionNameMapCache: OptionNameMap;
export function getOptionNameMap(): OptionNameMap {
if (optionNameMapCache) {
return optionNameMapCache;
}

let optionNameMap: Map<CommandLineOption> = {};
let shortOptionNames: Map<string> = {};
forEach(optionDeclarations, option => {
optionNameMap[option.name.toLowerCase()] = option;
if (option.shortName) {
shortOptionNames[option.shortName] = option.name;
}
});

optionNameMapCache = { optionNameMap, shortOptionNames };
return optionNameMapCache;
}

export function parseCommandLine(commandLine: string[]): ParsedCommandLine {
let options: CompilerOptions = {};
let fileNames: string[] = [];
let errors: Diagnostic[] = [];
let { optionNameMap, shortOptionNames } = getOptionNameMap();

parseStrings(commandLine);
return {
options,
Expand Down Expand Up @@ -345,13 +367,115 @@ namespace ts {
return parseConfigFileText(fileName, text);
}

/**
* Remove whitespace, comments and trailing commas from JSON text.
* @param text JSON text string.
*/
function stripJsonTrivia(text: string): string {
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I would split this out to a different change for now.

let ch: number;
let pos = 0;
let end = text.length - 1;
let result = '';
let pendingCommaInsertion = false;

while (pos <= end) {
ch = text.charCodeAt(pos);

if(isWhiteSpace(ch) || isLineBreak(ch)) {
pos++;
continue;
}

if(ch === CharacterCodes.slash) {
if (text.charCodeAt(pos + 1) === CharacterCodes.slash) {
pos += 2;

while (pos <= end) {
if (isLineBreak(text.charCodeAt(pos))) {
break;
}
pos++;
}
continue;
}
else if (text.charCodeAt(pos + 1) === CharacterCodes.asterisk) {
pos += 2;

while (pos <= end) {
ch = text.charCodeAt(pos);

if (ch === CharacterCodes.asterisk &&
text.charCodeAt(pos + 1) === CharacterCodes.slash) {

pos += 2;
break;
}
pos++;
}
continue;
}
}

if (pendingCommaInsertion) {
if (ch !== CharacterCodes.closeBracket &&
ch !== CharacterCodes.closeBrace) {

result += ',';
}
pendingCommaInsertion = false;
}

switch (ch) {
case CharacterCodes.comma:
pendingCommaInsertion = true;
break;

case CharacterCodes.doubleQuote:
result += text[pos];
pos++;

while (pos <= end) {
ch = text.charCodeAt(pos);
if (ch === CharacterCodes.backslash) {
switch (text.charCodeAt(pos + 1)) {
case CharacterCodes.doubleQuote:
result += "\\\"";
pos += 2;
continue;
case CharacterCodes.backslash:
result += "\\\\";
pos += 2;
continue;
}
pos++;
}
result += text[pos];

if (ch === CharacterCodes.doubleQuote) {
break;
}

pos++;
}
break;

default:
result += text[pos];
}

pos++;
}
return result;
}

/**
* Parse the text of the tsconfig.json file
* @param fileName The path to the config file
* @param jsonText The text of the config file
*/
export function parseConfigFileText(fileName: string, jsonText: string): { config?: any; error?: Diagnostic } {
try {
jsonText = stripJsonTrivia(jsonText);
return { config: /\S/.test(jsonText) ? JSON.parse(jsonText) : {} };
}
catch (e) {
Expand Down Expand Up @@ -425,7 +549,7 @@ namespace ts {
}
else {
let exclude = json["exclude"] instanceof Array ? map(<string[]>json["exclude"], normalizeSlashes) : undefined;
let sysFiles = host.readDirectory(basePath, ".ts", exclude).concat(host.readDirectory(basePath, ".tsx", exclude));
let sysFiles = host.readDirectory(basePath, ".ts", exclude).concat(host.readDirectory(basePath, ".tsx", exclude));
for (let i = 0; i < sysFiles.length; i++) {
let name = sysFiles[i];
if (fileExtensionIs(name, ".d.ts")) {
Expand Down
2 changes: 2 additions & 0 deletions src/compiler/diagnosticInformationMap.generated.ts
Original file line number Diff line number Diff line change
Expand Up @@ -517,6 +517,7 @@ namespace ts {
Option_sourceRoot_cannot_be_specified_with_option_inlineSourceMap: { code: 5049, category: DiagnosticCategory.Error, key: "Option 'sourceRoot' cannot be specified with option 'inlineSourceMap'." },
Option_mapRoot_cannot_be_specified_with_option_inlineSourceMap: { code: 5050, category: DiagnosticCategory.Error, key: "Option 'mapRoot' cannot be specified with option 'inlineSourceMap'." },
Option_inlineSources_can_only_be_used_when_either_option_inlineSourceMap_or_option_sourceMap_is_provided: { code: 5051, category: DiagnosticCategory.Error, key: "Option 'inlineSources' can only be used when either option '--inlineSourceMap' or option '--sourceMap' is provided." },
You_already_have_a_tsconfig_json_file_defined: { code: 5052, category: DiagnosticCategory.Error, key: "You already have a tsconfig.json file defined." },
Concatenate_and_emit_output_to_single_file: { code: 6001, category: DiagnosticCategory.Message, key: "Concatenate and emit output to single file." },
Generates_corresponding_d_ts_file: { code: 6002, category: DiagnosticCategory.Message, key: "Generates corresponding '.d.ts' file." },
Specifies_the_location_where_debugger_should_locate_map_files_instead_of_generated_locations: { code: 6003, category: DiagnosticCategory.Message, key: "Specifies the location where debugger should locate map files instead of generated locations." },
Expand Down Expand Up @@ -572,6 +573,7 @@ namespace ts {
Enables_experimental_support_for_emitting_type_metadata_for_decorators: { code: 6066, category: DiagnosticCategory.Message, key: "Enables experimental support for emitting type metadata for decorators." },
Option_experimentalAsyncFunctions_cannot_be_specified_when_targeting_ES5_or_lower: { code: 6067, category: DiagnosticCategory.Message, key: "Option 'experimentalAsyncFunctions' cannot be specified when targeting ES5 or lower." },
Enables_experimental_support_for_ES7_async_functions: { code: 6068, category: DiagnosticCategory.Message, key: "Enables experimental support for ES7 async functions." },
Initializes_a_TypeScript_project_and_creates_a_tsconfig_json_file: { code: 6069, category: DiagnosticCategory.Message, key: "Initializes a TypeScript project and creates a tsconfig.json file." },
Variable_0_implicitly_has_an_1_type: { code: 7005, category: DiagnosticCategory.Error, key: "Variable '{0}' implicitly has an '{1}' type." },
Parameter_0_implicitly_has_an_1_type: { code: 7006, category: DiagnosticCategory.Error, key: "Parameter '{0}' implicitly has an '{1}' type." },
Member_0_implicitly_has_an_1_type: { code: 7008, category: DiagnosticCategory.Error, key: "Member '{0}' implicitly has an '{1}' type." },
Expand Down
10 changes: 9 additions & 1 deletion src/compiler/diagnosticMessages.json
Original file line number Diff line number Diff line change
Expand Up @@ -161,7 +161,7 @@
},
"Type '{0}' is not a valid async function return type.": {
"category": "Error",
"code": 1055
"code": 1055
},
"Accessors are only available when targeting ECMAScript 5 and higher.": {
"category": "Error",
Expand Down Expand Up @@ -2057,6 +2057,10 @@
"category": "Error",
"code": 5051
},
"You already have a tsconfig.json file defined.": {
"category": "Error",
"code": 5052
},

"Concatenate and emit output to single file.": {
"category": "Message",
Expand Down Expand Up @@ -2278,6 +2282,10 @@
"category": "Message",
"code": 6068
},
"Initializes a TypeScript project and creates a tsconfig.json file.": {
"category": "Message",
"code": 6069
},

"Variable '{0}' implicitly has an '{1}' type.": {
"category": "Error",
Expand Down
Loading