At work we use clojurescript to implement a front-end with minified and 
gzipped assets coming in at around 170KB. If I can’t reduce that 
substantially I’ll probably have to rewrite in javascript. I’m posting to 
share some ideas I have for reducing the size of the script and to ask for 
any additional techniques others have used to get smaller scripts.

Things I can do right now:

   - Measure the impact of every library: I’ve found that transit adds 
   about 12KB gzipped and core.async adds even more (probably variable due to 
   the transformations performed by the go macro). Reagent is surprisingly 
   light - about 4KB. I’m using preact instead of react, so that lib is an 
   almost negligible 3KB. Importantly, I’ve found that some APIs provided by 
   google closure can have surprising impacts on script size. Don’t use 
   goog.xhr - do direct interop for http requests. 
   - Avoid multimethods and other global registries like re-frame. These 
   thwart DCE because there’s no way to know at compile time that a specific 
   method/handler is never used. 
   - Remove unnecessary parts of data structures. If you have a literal 
   vector of maps where each map has a key or two that isn’t used by code 
   (perhaps it’s just information for developers), those unused keys won’t be 
   DCE’d 
   - Make use of goog defines to get rid of code paths that you can 
   determine to be unnecessary at compile time. 
   - Avoid using apply for functions that implement a lot of different 
   arities. The clourescript compiler tends to be really smart about this - if 
   you implement 1, 2, and 3 arity versions of a function and only call the 
   two arity one, the 1 and 3 arity versions can get DCE’d. If you use apply, 
   however, all the arities end up in the script. 
   - Do a second round of minification with uglify or some other minifier. 
   I haven’t tested this in a while, but when I did last time it saved a KB or 
   two. At least it compresses the Math.imul definition at the top of the 
   script. 

Aside from dropping heavy libraries, those are all incremental changes. In 
order to get really substantial size savings, I think changes would need to 
be made to clojurescript. I have no idea about the feasibility of these 
things.

   - (ideally) automatically (but probably based on configuration) remove 
   unused methods of type definitions. For example, cljs.core.UUID implements 
   the equiv method of Object. Suppose we know at compile time that we will 
   construct UUIDs but not compare them with anything. It would be great to be 
   able to remove that method’s definition. I doubt this is possible without a 
   static type system, but I wonder whether there is some way to make this 
   configurable that wouldn’t lead to an explosion of configuration options 
   and inscrutable errors. 
   - Some functions implement multiple arities for dispatch performance. I 
   would like to be able to say “I accept the performance hit in exchange for 
   only implementing one arity of this function”. For instance, partial 
   implements multiple arities of its own args and of the function it returns. 
   This could be reduced down to (defn partial [f & more] (fn [& args] (apply 
   f (concat more args)))) if we cared more about script size than runtime 
   performance. 

Any other ideas?
​

-- 
Note that posts from new members are moderated - please be patient with your 
first post.
--- 
You received this message because you are subscribed to the Google Groups 
"ClojureScript" group.
To unsubscribe from this group and stop receiving emails from it, send an email 
to clojurescript+unsubscr...@googlegroups.com.
To post to this group, send email to clojurescript@googlegroups.com.
Visit this group at https://groups.google.com/group/clojurescript.

Reply via email to