2

Closed

Wrong output order for single file compilation

description

From: https://typescript.codeplex.com/discussions/456585
Possibly related to: https://typescript.codeplex.com/workitem/913

I'd like to note for the dev team that there are issues with regular inheritance, not only with circular references.

I saw paulb's comments that some things are by design, but this doesn't seem like it.

My code is quite simple, A extends B, C extends B, but depending on which folder the files are, they are compiled in the wrong order and this keeps changing depending on which file I change later.

This seems to happen only if you have classes in different directories, and makes it impossible to use single file output for anything other than samples.
Closed Sep 17, 2013 at 12:31 AM by RyanCavanaugh
I can't reproduce the problem in the case where the files have correct reference tags (the other cases are unsupported at this time).

If you're still having problems with compile-on-save when the files have correct reference tags, can you post a comment with a concise description of what you're doing? This will need to be fairly exact -- the order in which you opened the files and which you have open are potentially a factor here. Thanks!

comments

paulb wrote Sep 14, 2013 at 5:36 PM

Thanks for reporting, we need a little more information here.

Does this happen in Visual Studio with Compile on Save, or when doing a build? Does this happen when doing a command line compile? If so what is the exact command line you use?

nvivo wrote Sep 16, 2013 at 3:21 PM

Sorry about the long comment, it took me sometime to understand how to reproduce this in all cases I saw.

Here is the setup:

Had "Compile on Save" enabled on VS, created a new TypeScript HTML project, delete everything and replace the TS project settings with:
<PropertyGroup>
  <TypeScriptTarget>ES5</TypeScriptTarget>
  <TypeScriptOutFile>$(WebProjectOutputDir)\Out.js</TypeScriptOutFile>
</PropertyGroup>
Reload the project and create a structure like this:

C.ts -> type "class C {}" and save
B.ts -> type "class B extends C {}" and save
A\A.ts -> type "class A extends B {}" and save

We can already see the problem at Out.js:
var __extends = ...;
var A = (function() { ... })(B);
var B = (function() { ... })(C);
var C = (function() { ... })();
I called TSC manually and it seems TSC just follows the order the files are passed to it, and VS must be passing in alphabetic order

Calling "tsc -out Out.js A\A.ts B.ts C.ts" produces the same output (B, C, A).
Calling "tsc -out Out.js C.ts B.ts A\A.ts" produces it in the correct order (C, B, A)

Now, I tried adding the references clause to the files so it knows the dependencies, and there are some odd issues.

Added references to both files in this order and saved them right after adding the references:
/// <reference path="C.ts" />
class B extends C { }
Out.js will have A, C, B. Then I added:
/// <reference path="../B.ts" />
class A extends B { }
Out.js will remain A, C, B even though the file was recompiled for sure. I did it slowly one after another, and gave it time to show the "file was changed" alert. Now, saving any of the files again will compile them in the correct order (C, B, A).
At this point, calling TSC in any order outputs the files correctly, so it seems something related to VS incremental compilation.

Now, I decided to change the references to point to a single _references.ts in the root, because this is how I usually work having lots of references:
_references.ts have:
/// <reference path="A/A.ts" />
/// <reference path="B.ts" />
/// <reference path="C.ts" />
After saving each file in any order, the output remains "A, B, C", as the order of references in _references.ts.

Now, if I do a Ctrl+Shift+B, it turns into "B, C, A". Saving any file later goes back to "A, B, C". This seems to be the issue I noticed about the ordering changing depending on what I did in VS.

Compiling with TSC at this point produces all kinds of ordering
tsc -out Out.js A\A.ts B.ts C.ts -> B, C, A
tsc -out Out.js B.ts A\A.ts C.ts -> A, C, B
tsc -out Out.js C.ts B.ts A\A.ts -> C, A, B
tsc -out Out.js B.ts C.ts A\A.ts -> A, C, B
tsc -out Out.js A\A.ts C.ts B.ts -> B, C, A
tsc -out Out.js C.ts A\A.ts B.ts -> C, B, A
It seems to me that without automatic file reordering, the only way to order the files correctly in single output in a sane way is to not add any references to any file, and call tsc manually passing the files in order. Anything else currently will get anyone crazy. But this makes VS integration useless when compiling to a single file.

I don't think TSC should reorder file contents, but it should at least try to order the files the best it can without caring about the order the references are added.

Paul0515 wrote Mar 10 at 9:54 AM

Why is this closed? nvivo made impressive work on explaining the issue, jet the reason it was closed, is 'Need more info'. Seems still relevant to me.

danquirk wrote Apr 1 at 8:16 PM

This should have been remedied by _references.ts support in VS. That allows you to control the file order to tsc. If there are still issues here with the latest TypeScript please re-open this or file a new issue and we can track down what's happening.