Theoretically, we can build a better optimizer/minifier than Google since they have to be general purpose and we know the patterns in our code.
I've mentioned adding a super-strict compiler option before. It would warn on every Object and * type resolution. Maybe that would help? Does it matter whether you remove unused classname strings before or after minification? Maybe a post-processor can remove all className strings that aren't implementing IUIBase if you know you don't need them. We discussed ways of shortening private names in the past as well. Maybe it is time to implement that. -Alex On 12/28/21, 1:36 PM, "Harbs" <harbs.li...@gmail.com> wrote: After 2 weeks of intense work, I got my app fully functional with the options below. Here’s in short what I did: 1. I audited as many cases of quoted access I could in the unminified JS code. Any place where it was accessing something on a class/instance was because the compiler couldn’t figure out the type. 2. I added types to all the places I could find. I basically eliminated every use of :Object and :* that I could. 3. I used Vectors where I could (using the -js-vector-emulation-class=Array option) 4. I removed unknown class accessors (no looping through classes and calling static methods) 5. Removed all the dynamic bracket access and assignment. (no for-ins on class instances, etc.) In my travels I discovered that: 1. Jewel does not look like it can be aggressively minified. (Spectrum can.) 2. MX/Spark does not look like it can either. 3. I need to heavily modify my already modified version of TLF to get it to work with minification. 4. There was some unnecessary Reflection and Vector dependencies in framework code which I fixed. 5. Class names is a prime candidate for code removal, and (besides reflection) the current roadblock with that is SimpleCSSValuesImpl which accesses ROYALE_CLASS_INFO. If we can eliminate that, I’d save 66KB (12KB gzipped) in my app. 6. It’s worthwhile to use protected methods for event listener callbacks, because the long-winded private method names end up in the minified code. (I still need to address this.) End results: Before my effort, my app was 2,903,814 bytes and 777,071 bytes when gzipped Afterwards: 1,989,596 bytes and 621,851 bytes gzipped That’s a savings of 1MB before gzipping (about 1/3) and 155KB after gzipping. (about 20% reduction) If we can get rid of the class names we can get down to: 1,923,653 bytes/610,493 bytes. A little over 600KB is a totally reasonable size for an application of this size and complexity. The Flash version was MANY times that and has a LOT less code. This turned into somewhat of an obsession for me, but I’m pleased with the results. :-) HTH, Harbs > On Dec 16, 2021, at 8:54 PM, Harbs <harbs.li...@gmail.com> wrote: > > Well I spent more time. Besides the XML issues which are pretty much resolved, I ran into: > > 1. I have a setter in a class which was removed by the goog dead code removal. I worked around it by turning the setter into a method. I’ll see if I can come up with a minimal test case on that. > > 2. I have a library which has a LOT of dynamic pieces. I spent a LONG time trying to assign types to places where I was getting runtime errors. I now got to the point where there’s no more runtime errors, but it’s still not working and I’m pretty sure it’s because I missed some typing. > > Is there any way to keep public accessors on one library or specific classes? I’d like to compile my app with: > > "-js-dynamic-access-unknown-members=true", > "-export-public-symbols=false", > "-prevent-rename-protected-symbols=false", > "-prevent-rename-public-symbols=false", > "-prevent-rename-internal-symbols=false" > > but be able to exclude a list of classes from that. > >> On Dec 1, 2021, at 7:47 PM, Harbs <harbs.li...@gmail.com <mailto:harbs.li...@gmail.com>> wrote: >> >> I’m pretty sure the issue is related to events not being properly handled. Although blinding might be worth looking into. >> >> I’ll look into it some more when I have more time. >> >> Thanks! >> >>> On Dec 1, 2021, at 7:14 PM, Josh Tynjala <joshtynj...@bowlerhat.dev <mailto:joshtynj...@bowlerhat.dev>> wrote: >>> >>>> It *almost* works. I found and fixed two cases of bracket access which >>> broke things. Now I’m getting no errors, but it’s still not quite working. >>> I’m guessing it’s something simple that I need to fix. >>> >>> Have you tried a smaller set of prevent-rename options? That might help you >>> narrow things down, if things start working better. I'd try allowing public >>> variables, and maybe public accessors, to be renamed first, and see if that >>> works. Those types of symbols are most likely to be getting accessed >>> dynamically somehow. However, I don't really have much in the way of tips >>> to narrow it down from there. ConstantBinding would be one thing to look >>> out for, which I mentioned in my summary. >> >