Hey folks, I just pushed some commits to royale-compiler and royale-asjs, and I wanted to add a little explanation, and some possible troubleshooting advice if anything seems to have broken in your apps.
My work over the last week has been to fix an issue related to specifying dependencies when compiling libraries for JS. As you probably know, the compiler supports two options for adding libraries as dependencies, library-path and external-library-path. The library-path compiler option basically says "include all classes that I use from this SWC in the final output". It's typically what you use when compiling an app that uses a library. The external-library-path compiler option basically says "if I use anything from this SWC, check that I'm using the types correctly, but don't include any of classes from this SWC in the final output". If you're compiling an app, you typically use library-path for everything. You use external-library-path only for dependencies like playerglobal.swc/airglobal.swc in Flash or typedef SWCs in JS. Basically, for an app project, external-library-path is for classes that are provided natively by the Flash runtime or a web browser, like Chrome or Firefox. When compiling libraries, external-library-path is also used to prevent the compiler from creating a "fat" library that stuffs in all of the dependencies. Let's say that you have a library, A.swc. It provides some core functionality that is needed by both B.swc and C.swc. When we compile B.swc and C.swc, we don't want the classes from A.swc duplicated in both of them. So we add A.swc to the external-library-path when compiling B.swc or C.swc. Then, if you use those SWCs when compiling an app, you need to add A.swc, B.swc, and C.swc to the library-path. To put that in Royale terms, A.swc is something like LanguageJS.swc or CoreJS.swc. They're some of our lowest-level SWCs in the framework. B.swc and C.swc are more like BasicJS.swc or JewelJS.swc, and they tend to share multiple classes from the lower-level stuff. Up until now, library-path and external-library-path were a little quirky when compiling to JS. It was related to the goog.provide() and goog.require() calls that you might have seen in the generated JS. These are from the module system that we use in Royale. The compiler didn't know how to differentiate between classes that had goog.provide() and classes that were typedefs for JS libraries. It treated everything on the external-library-path as a typedef, and this led to missing goog.require() calls in the generated JS. To work around this, when we specified dependencies in our framework SWCs, we used library-path to ensure that goog.require() would be used. This workaround of using library-path led to "fat" SWCs that contained all of their dependencies. Low-level classes in SWCs like CoreJS were duplicated in higher-level SWCs. This led to the compiler getting confused about exactly where a class was defined. This has resulted in some minor issues here and there, but nothing too major until recently. However, Harbs noticed the other day that it caused the compiler to copy extra default CSS into apps from SWCs that you may not have been using. So, you might build an app with the Basic components, but you'd get extra CSS from Jewel or MaterialDesignLite. This could mess up your app's styling pretty dramatically. I updated the compiler to better detect when a class needs goog.require() and when it's a typedef. If that class comes from a SWC, the compiler knows to check for an included file like, js/out/com/example/MyClass.js. If the generated JS is there, goog.require() is necessary. If it's missing, it's treated as a typedef class instead. If the class is an .as source file instead, the compiler looks for the @externs asdoc tag to determine if it's a typedef class (and everything else needs goog.require() instead). By the way, if we ever support other module systems, it shouldn't be too difficult to extend this code to detect different SWC layouts for each module system. If your project is an app, this change should not cause any problems. You're probably using library-path and external-library-path correctly. If you have a project that is a library, you should check your compiler options to see if you are using library-path and external-library-path correctly. If your library depends on another library, you probably should be using external-library-path because you don't want a "fat" SWC. In other words, if you're using library-path in a library project, you probably need to change that to external-library-path. If you have any custom typedef SWCs, you may want to recompile them. At one point, the compiler had a bug where classes in typedef SWCs were being incorrectly added to the "js/out" folder in the SWC, but that was incorrect. They should have been placed in an "externs" folder instead. The compiler handles this correctly now, but old typedef SWCs may look like goog.require() SWCs instead. To be sure, you can open a SWC file in any program that can read ZIP files, and you'll see the internal folder structure. If a typedef SWC has a "js/out" folder, it's not going to work properly. If you're working directly out of the royale-compiler and royale-asjs Git repos, be sure to update and rebuild them both. The nightly builds should be updated shortly. When you build any apps, be sure to clean first, just to be sure that you have the latest JS files from the SWCs. If you run into any other problems with these changes, please let me know. I'll get them fixed right away! -- Josh Tynjala Bowler Hat LLC <https://bowlerhat.dev>