magnars / optimus

A Ring middleware for frontend performance optimization.
364 stars 23 forks source link

Help with building a babel.js middleware #73

Open rutchkiwi opened 4 years ago

rutchkiwi commented 4 years ago

Hi! This is not really a bug but more of a question, apologies up front if there is a better place for this sort of thing and I will take my question there.

I want to use ES6 features in my javascript files, but I need to support IE11 so I want to make a middleware for Babel to complie my ES6 to ES5. (https://babeljs.io/docs/en/next/babel-standalone.html).

Is there a preffered example of a JS middleware that I can look at to try and get started? I tried to look through some of the other middlewares listed in the readme but they all seem to use different JS engines etc - is there a newest and best one that you'd reccomend?

(Also, thanks a lot for this awesome library - without it I don't think it would've been possible to build a customer-facing website like the one of my company!)

magnars commented 4 years ago

Hi Viktor! I'm glad to hear Optimus is helping you out. :) Building optimized customer-facing websites is just why I wrote Optimus in the first place.

Adding an optimus-middleware that runs Babel sounds entirely doable. We are just now in the process of releasing 1.0, with support for Windows and switching to pluggable JS-engines, with GraalJS as a default.

This means that writing plugins for the old V8 engine is not recommended, and a new example is still missing. I am currently working on porting the optimus-autoprefixer to the new scheme. Once that is done, you can use that as a good starting point.

Sound ok? I can ping you in this thread once that is ready.

rutchkiwi commented 4 years ago

Thank you Magnars! Sounds great, please let me know :) I should be able to run Babel manually in the meantime

magnars commented 4 years ago

Hi again. :) I have now ported my own JS-based middleware to the new 1.0.0-API. You can check it out here: https://github.com/magnars/optimus-autoprefixer

Let me know if you have any questions!

magnars commented 4 years ago

(note that this must be used with the new Optimus, currently at 1.0.0-rc3)

rutchkiwi commented 4 years ago

That was fast! Thanks a lot - looks like the new interface is very simple! I will try to get something working in the coming weeks.

rutchkiwi commented 4 years ago

Hey I managed to get something running but it is running excruciatingly slow - I suspect it's something related to the graal vm running the JS:

Using babel downloaded from https://unpkg.com/@babel/standalone@7.7.6/babel.min.js

(defn escape [s]
  (-> s
      (str/replace "\\" "\\\\")
      (str/replace "'" "\\'")
      (str/replace "\n" "\\n")))

(defn normalize-line-endings [s]
  (-> s
      (str/replace "\r\n" "\n")
      (str/replace "\r" "\n")))

(defn prepare-engine []
  (log/debug "preparing engine")
  (let [engine (js/make-engine)]
    (.eval engine (slurp (clojure.java.io/resource "babel.min.js")))
    engine))

(def js-code (slurp "semi-big js file path here")

(js/run-script-with-error-handling (js/make-engine) 
                                   (format "(function(){
      return Babel.transform('%s', {presets: ['es2015']}).code
    })()" (escape (normalize-line-endings js-code))) {})

This takes around 11s for a JS file of a thousand lines - and even a micro js file like "console.log('hello')" takes 40-50 ms. (and about 30ms more for each new line)

The entire file which took 11 s in this setup took around 50 ms when I used the babel CLI.

Do you have any ideas as to what could be causing this? Or is this just how it is with graalvm? Appricate any help!

magnars commented 4 years ago

In my (admittedly limited) testing, the performance of the graaljs runtime was pretty similar to the old V8 binaries we were using before, but I haven't compared it to just running on node. Three orders of magnitude worse makes me think something is pretty off.

Looking at this: https://github.com/graalvm/graaljs/issues/74 - there seems to be some JVM-flags you could try out? I'm in the middle of work now, but if you get anything out of this, please do let me know.

rutchkiwi commented 4 years ago

Thank you - I will have a look when I can!

frank-dspeed commented 2 years ago

https://github.com/oracle/graaljs/issues/74 is now solved with most current graal release enjoy a up to 70x faster graal-node

magnars commented 2 years ago

@frank-dspeed Wow, that's amazing! Since we're interop'ing with graal only via JSR223, how would one go about getting these performance improvements? An explicit dependency on graal? Upgrading java version?

frank-dspeed commented 2 years ago

updating graaljs is enough it now got a new string implementation and that was the problem with the old one also graal-node which comes with graaljs got a new boot mode that can transition between fast boot and peak performance

you should use the current 22.1 release https://www.graalvm.org/downloads/