I'll try to fill in the details soon. -- Josh Tynjala Bowler Hat LLC <https://bowlerhat.dev>
On Fri, Nov 20, 2020 at 11:42 AM Andrew Wetmore <cottag...@gmail.com> wrote: > I have added a section that includes the four compiler options that Carlos > mentioned. If there are more that, when used, reduce output size, they > should go there. I have not populated the descriptions, as a smart person > should do that. > > a > > On Fri, Nov 20, 2020 at 3:23 PM Andrew Wetmore <cottag...@gmail.com> > wrote: > > > Yes, that page is a good location. Should we start a subsection for these > > options which have the benefit of reducing output size? > > > > a > > > > On Fri, Nov 20, 2020 at 1:48 PM Carlos Rovira <carlosrov...@apache.org> > > wrote: > > > >> Hi Josh, > >> > >> thanks for working on this. I finally could get here after weeks of hard > >> work in other things with almost not time. > >> I tried in Tour de Jewel with: > >> > >> -export-public-symbols=false > >> -prevent-rename-protected-symbols=false > >> -prevent-rename-internal-symbols=false > >> -prevent-rename-public-static-methods=false > >> -prevent-rename-public-instance-methods=false > >> > >> (for what I read that's the set it can be used without breaking app) > >> > >> and a downsize from 1045kb to 910kb so amazing! :) > >> > >> I'll try to add to TodoMVC as well and see what happens ;) > >> > >> @Andrew I think you and Josh can add this doc to the Royale Docs > compiler > >> options page here [1] > >> > >> [1] https://apache.github.io/royale-docs/compiler/compiler-options > >> > >> > >> > >> El mar, 10 nov 2020 a las 23:36, Josh Tynjala (< > joshtynj...@bowlerhat.dev > >> >) > >> escribió: > >> > >> > Hi Andrew, > >> > > >> > Yes, I can help with that! > >> > > >> > -- > >> > Josh Tynjala > >> > Bowler Hat LLC <https://bowlerhat.dev> > >> > > >> > > >> > On Mon, Nov 9, 2020 at 3:22 PM Andrew Wetmore <cottag...@gmail.com> > >> wrote: > >> > > >> > > Josh, this is very interesting. I would like to include an > actionable > >> > > amount of this information in our user documentation. If I create a > >> page > >> > in > >> > > the help docs for it, can you help me populate instructions based on > >> your > >> > > researchs? > >> > > > >> > > Thanks! > >> > > > >> > > Andrew > >> > > > >> > > On Mon, Nov 9, 2020 at 6:16 PM Josh Tynjala < > >> joshtynj...@bowlerhat.dev> > >> > > wrote: > >> > > > >> > > > Hi all, > >> > > > > >> > > > Some of you have probably been wondering about my changes to the > >> > compiler > >> > > > over the last year or more. I apologize again for occasionally > >> breaking > >> > > > things for short periods. It's been quite a challenge getting this > >> > stuff > >> > > > working, but I'm excited to finally be able to report some real > >> > > > improvements that pretty much anyone should be able to take > >> advantage > >> > of > >> > > > when building a Royale app. > >> > > > > >> > > > First some background. A while back, Harbs asked me to look into > >> ways > >> > of > >> > > > reducing the file size of release builds. As you may know, we use > >> > > Google's > >> > > > Closure compiler to optimize our generated JavaScript. Closure can > >> be > >> > > very > >> > > > aggressive in its optimizations, by renaming symbols (things like > >> > > variable > >> > > > and function names) and removing "dead code" that is detected as > >> never > >> > > > being called. > >> > > > > >> > > > Closure's optimizations are good, but they also require developers > >> to > >> > be > >> > > > very careful about how they write their JavaScript code. When you > >> > enable > >> > > > Closure's full optimizations, you are not allowed to use certain > >> > > JavaScript > >> > > > features because Closure cannot analyze them properly. For > instance, > >> > > > consider the following code: > >> > > > > >> > > > var propName= "myProp"; > >> > > > var value = obj[propName]; > >> > > > > >> > > > When you dynamically access a property with a string, Closure > cannot > >> > > > reliably know that the property exists and will be accessed at > >> runtime. > >> > > It > >> > > > may decide to rename or remove that property, which would break > >> things > >> > at > >> > > > runtime. > >> > > > > >> > > > ActionScript supports many of the same restricted dynamic features > >> too, > >> > > so > >> > > > if you want to support the entire AS3 language, we can't let > >> Closure do > >> > > its > >> > > > full optimization. Luckily, Closure also provides a bit of a > >> backdoor: > >> > it > >> > > > allows you to "export" symbols, which means that they won't be > >> renamed > >> > > and > >> > > > they won't be removed as dead code. Traditionally, we have made > >> heavy > >> > use > >> > > > of this exporting feature in Royale. > >> > > > > >> > > > Harbs wanted to know if we absolutely needed to export everything > >> that > >> > we > >> > > > currently export, and if we could potentially allow developers to > >> turn > >> > > off > >> > > > exporting entirely, as long as they follow the stricter rules > >> required > >> > by > >> > > > Closure. > >> > > > > >> > > > I won't go into all of the details, but over the last several > >> months, > >> > > I've > >> > > > been changing the compiler to give developers more control over > >> release > >> > > > builds. In particular, control over which symbols get exported, > but > >> > also > >> > > > the ability to block Closure from renaming symbols that haven't > been > >> > > > exported. > >> > > > > >> > > > Now, for some of the results. I'm going to share the output file > >> size > >> > of > >> > > > the release build for several Royale projects with various > different > >> > > > compiler options. > >> > > > > >> > > > For the example projects included with Royale, I built royale-asjs > >> > commit > >> > > > 94f12ed0e564b0b443834400dc2fc06d61b90a8a from October 26, 2020. If > >> you > >> > > want > >> > > > to try building these examples yourself, the file sizes of release > >> > builds > >> > > > may be slightly different, if you use a different commit. > >> > > > > >> > > > SpectrumBrowser is a project developed by Harbs and his team. I > used > >> > > commit > >> > > > d25a3def972b15ec029ae838f1a8a677d2d158bd from October 20 for the > >> > results > >> > > > below. Repo: https://github.com/unhurdle/spectrum-royale/ > >> > > > > >> > > > To establish a baseline, I built all of these projects with the > >> older > >> > > > Royale 0.9.7 compiler first. > >> > > > > >> > > > ========== > >> > > > Baseline: royale-compiler 0.9.7 > >> > > > ========== > >> > > > > >> > > > HelloWorld: 68 KB > >> > > > ASDoc: 231 KB > >> > > > TourDeJewel: 1074 KB > >> > > > SpectrumBrowser: 900 KB > >> > > > > >> > > > Again, I am building the same AS3/MXML code every time, but these > >> first > >> > > > numbers are from building with the older compiler. All apps build > >> and > >> > run > >> > > > successfully. > >> > > > > >> > > > ----- > >> > > > > >> > > > The rest of the results are built with royale-compiler commit > >> > > > df8bd9f686f1bbf89539e545377b2797c646172c from November 3. > >> > > > > >> > > > All results below include the difference in KB and %. These values > >> are > >> > > > always in comparison to the baseline numbers above. > >> > > > > >> > > > ========== > >> > > > Result 1: 0.9.8 default options > >> > > > ========== > >> > > > > >> > > > HelloWorld: 84 KB (+10 KB / +24%) > >> > > > ASDoc: 254 KB (+23 KB / +10%) > >> > > > TourDeJewel: 1105 KB (+31 KB / +3%) > >> > > > SpectrumBrowser: 936 KB (+36 KB / +4%) > >> > > > > >> > > > These examples are slightly larger when built with the newer > >> compiler. > >> > > > That's expected. It's not ideal, but in the process of testing a > >> > > multitude > >> > > > of things to be sure that nothing had broken after my compiler > >> > changes, I > >> > > > discovered some cases where exporting a symbol didn't actually > work > >> > > > correctly in 0.9.7! To properly fix the bug and export these > >> symbols, > >> > > there > >> > > > was no choice but to make the file size a bit larger. > >> > > > > >> > > > ========== > >> > > > Result 2: Disable export > >> > > > ========== > >> > > > > >> > > > HelloWorld: 74 KB (+6 KB / +9%) > >> > > > ASDoc: 227 KB (-4 KB / -2%) > >> > > > TourDeJewel: 942 KB (-132 KB / -12%) > >> > > > SpectrumBrowser: 882 KB (-18 KB / -2%) > >> > > > > >> > > > In this round, I added the *-export-public-symbols=false* compiler > >> > > option. > >> > > > You may recall that I said earlier that I also modified the > >> compiler to > >> > > > allow a symbol not to be exported, but still prevent it from being > >> > > renamed. > >> > > > With that in mind, -export-public-symbols=false basically tells > the > >> > > > compiler that it still can't rename things, but it is allowed to > >> remove > >> > > > what it perceives as dead code. > >> > > > > >> > > > HelloWorld is still slightly larger than 0.9.7, but the three > other > >> > > > examples are now slightly smaller than 0.9.7. > >> > > > > >> > > > Most developers should be able to safely add > >> > -export-public-symbols=false > >> > > > to their compiler options when building a Royale app. The only > time > >> > that > >> > > > you might still want this exporting is if you have external > >> JavaScript > >> > in > >> > > > your page that isn't part of your Royale app, but it needs to call > >> > > > functions/classes in your Royale app. > >> > > > > >> > > > ========== > >> > > > Result 3: Allow non-public things to be renamed > >> > > > ========== > >> > > > > >> > > > HelloWorld: 72 KB (+4 KB / +6%) > >> > > > ASDoc: 221 KB (-10 KB / -4%) > >> > > > TourDeJewel: 918 KB (-156 KB / -15%) > >> > > > SpectrumBrowser: 861 KB (-39 KB / -4%) > >> > > > > >> > > > In this round, I used the following compiler options: > >> > > > > >> > > > -export-public-symbols=false > >> > > > > >> > > > > >> > > > > >> > > > >> > > >> > *-prevent-rename-protected-symbols=false-prevent-rename-internal-symbols=false* > >> > > > > >> > > > The two new options allow Closure compiler to rename protected and > >> > > internal > >> > > > symbols. Once again, HelloWorld is still slightly larger than > 0.9.7, > >> > but > >> > > > the other three examples have gotten smaller again. > >> > > > > >> > > > While -prevent-rename-public-symbols=false exists too, we cannot > use > >> > it. > >> > > > The examples would not work correctly at runtime. This option > would > >> > > > probably work in a pure AS3 app, but our implementation of MXML in > >> > Royale > >> > > > uses dynamic language features that Closure restricts. Unless that > >> is > >> > > > fixed, we need to avoid renaming certain public symbols. > >> > > > > >> > > > Again, most developers should be able to add > >> > > > -prevent-rename-protected-symbols=false > >> > > > and -prevent-rename-internal-symbols=false to their Royale app's > >> > compiler > >> > > > options. You might need to prevent renaming of protected/internal > >> > symbols > >> > > > if you access them dynamically. However, in my experience, people > >> are > >> > > much > >> > > > more likely to access public symbols dynamically. > >> > > > > >> > > > ----- > >> > > > > >> > > > ========== > >> > > > Result 4: Allow public methods to be renamed > >> > > > ========== > >> > > > > >> > > > HelloWorld: 64 KB (-4 KB / -6%) > >> > > > ASDoc: 206 KB (-25 KB / -11%) > >> > > > TourDeJewel: 881 KB (-193 KB / -18%) > >> > > > SpectrumBrowser: 828 KB (-72 KB / -8%) > >> > > > > >> > > > In this round, I used the following compiler options: > >> > > > > >> > > > -export-public-symbols=false > >> > > > -prevent-rename-protected-symbols=false > >> > > > -prevent-rename-internal-symbols=false > >> > > > > >> > > > > >> > > > > >> > > > >> > > >> > *-prevent-rename-public-static-methods=false-prevent-rename-public-instance-methods=false > >> > > > * > >> > > > > >> > > > The two new options allow Closure to rename methods that are > public. > >> > Now, > >> > > > all four examples are smaller than 0.9.7, and the file size > >> difference > >> > is > >> > > > getting even more dramatic. > >> > > > > >> > > > Once again, -prevent-rename-public-static-methods=false and > >> > > > -prevent-rename-public-instance-methods=false should be safe for > >> most > >> > > > developers to enable when compiling their Royale app. In my > >> experience, > >> > > > calling methods dynamically is rare. > >> > > > > >> > > > ========== > >> > > > More new compiler options > >> > > > ========== > >> > > > > >> > > > There are some additional new compiler options available, but > using > >> > them > >> > > is > >> > > > likely to break most Royale apps. > >> > > > > >> > > > -prevent-rename-public-static-variables=false > >> > > > -prevent-rename-public-instance-variables=false > >> > > > -prevent-rename-public-static-accessors=false > >> > > > -prevent-rename-public-instance-accessors=false > >> > > > > >> > > > These options control whether Closure allows variables or > accessors > >> > > > (getters and setters) to be renamed. There are also > similarly-named > >> > > options > >> > > > for protected and internal symbols, if you want more control over > >> those > >> > > > too, instead of using -prevent-rename-protected-symbols=false and > >> > > > -prevent-rename-internal-symbols=false. > >> > > > > >> > > > Unfortunately, renaming public variables/accessors is usually not > >> > > possible > >> > > > without breaking the app at runtime. In some apps, you might be > >> able to > >> > > > allow public static members to be renamed. However, in my > >> experience, > >> > > > binding to static constants is pretty common, and renaming breaks > >> those > >> > > > bindings. > >> > > > > >> > > > ========== > >> > > > Next Steps > >> > > > ========== > >> > > > > >> > > > Ideally, I'd like to make it possible for developers to be able to > >> tell > >> > > > Closure that it's allowed to rename all symbols, including public > >> > ones. I > >> > > > believe that we could see even more file size savings in release > >> builds > >> > > if > >> > > > Closure works with full optimizations for all symbols. Obviously, > >> > > > ActionScript developers would be required to strictly follow > >> Closure's > >> > > > rules, if they opt into renaming of public symbols, but that's a > >> choice > >> > > > that they should be allowed to make. > >> > > > > >> > > > As I mentioned above, our implementation of MXML and binding uses > >> > dynamic > >> > > > access, which is not compatible with Closure's full optimizations. > >> To > >> > > > support those optimizations, I will need to explore changes to how > >> we > >> > > > generate JS for MXML, and how it gets parsed at runtime. > >> > > > > >> > > > We previously discussed this subject a bit in this older thread > from > >> > > > January 2020: > >> > > > > >> > > > > >> > > > > >> > > > >> > > >> > https://lists.apache.org/thread.html/r843e55252e37967b71b1430a2a904719791d698f3e5e2a79de74e493%40%3Cdev.royale.apache.org%3E > >> > > > > >> > > > At the time, I tried out some ideas that we came up with while > >> > > > brainstorming, but all had various downsides that didn't make for > an > >> > > > obvious winner. In the end, I decided to set further investigation > >> > aside > >> > > > and first focus on exporting/renaming stuff. Now, I'm ready to > take > >> a > >> > > > second look with a fresh perspective, and maybe we'll have some > new > >> > ideas > >> > > > to try. > >> > > > > >> > > > ----- > >> > > > > >> > > > That was really long, so thank you for reading, if you made it to > >> the > >> > > end! > >> > > > > >> > > > TL;DR: By enabling certain, new compiler options, most Royale > >> > developers > >> > > > can make their app release builds smaller. Additionally, I plan to > >> keep > >> > > > investigating, and I expect to find more ways to reduce file size > in > >> > the > >> > > > future. > >> > > > > >> > > > -- > >> > > > Josh Tynjala > >> > > > Bowler Hat LLC <https://bowlerhat.dev> > >> > > > > >> > > > >> > > > >> > > -- > >> > > Andrew Wetmore > >> > > > >> > > http://cottage14.blogspot.com/ > >> > > > >> > > >> > >> > >> -- > >> Carlos Rovira > >> Apache Member & Apache Royale PMC > >> *Apache Software Foundation* > >> http://about.me/carlosrovira > >> > > > > > > -- > > Andrew Wetmore > > > > http://cottage14.blogspot.com/ > > > > > > > > > > > > -- > Andrew Wetmore > > http://cottage14.blogspot.com/ >