ember-cli / ember-cli

The Ember.js command line utility.
https://cli.emberjs.com
MIT License
3.26k stars 1.16k forks source link

Build times (initial and subsequent) 2x-4x slower after 0.1.5 upgrade #2856

Closed beerlington closed 9 years ago

beerlington commented 9 years ago

I upgraded from 0.1.2 to 0.1.5 and am seeing a 2x initial build time slowdown and a 4x subsequent rebuild time slowdown. The initial build time is tolerable because it only happens once, but having to wait > 4x longer when saving changes is a bit tedious during development. I initially upgraded on a MacBook Air and thought it was a fluke, but I've since done is on a fairly beefy iMac and am seeing the same results.

I created a gist showing a comparison of 0.1.2 vs 0.1.5 build times, but here's a short summary of what I'm seeing:

0.1.2 rebuild

Build successful - 675ms.

Slowest Trees                  | Total          
-------------------------------+----------------
LessCompiler                   | 148ms          
ES6Concatenator                | 84ms           
ES3SafeFilter                  | 70ms           
JSHint - App                   | 65ms           
JSHint - Tests                 | 49ms           
TemplateCompiler               | 36ms 

0.1.5 rebuild

Build successful - 2951ms.

Slowest Trees                  | Total          
-------------------------------+----------------
LessCompiler                   | 1045ms         
Class                          | 333ms          
Class                          | 241ms          
Class                          | 205ms          
Funnel                         | 202ms 

I searched through the open and closed issues from the last month or so and don't see anything similar to what I'm seeing. I'm also using Ember 1.9 (not 1.8.1 which is what ember init suggests I use), so perhaps that version is not yet supported?

rwjblue commented 9 years ago

Can you share:

stefanpenner commented 9 years ago

Or even better make a OSS repo that demonstrates this

beerlington commented 9 years ago

I'll see if I can create an open source project based on the one I'm referencing later today, but for now here's the info requested:

app/: 356 files, 1.5MB total bower_components/: 2,453 files, 25MB total public/: 62 files, 1.9MB

I can't think of anything else that might be related, but maybe something will come up if I can recreate it in an OSS project as @stefanpenner suggested.

package.json

  "devDependencies": {
    "broccoli-asset-rev": "^2.0.0",
    "ember-autoresize": "^0.2.5",
    "ember-cli": "^0.1.5",
    "ember-cli-async-button": "^0.3.0",
    "ember-cli-dependency-checker": "0.0.7",
    "ember-cli-esnext": "0.1.1",
    "ember-cli-google-analytics": "~1.1.0",
    "ember-cli-htmlbars": "^0.6.0",
    "ember-cli-ic-ajax": "0.1.1",
    "ember-cli-inject-live-reload": "^1.3.0",
    "ember-cli-less": "^1.0.4",
    "ember-cli-moment": "0.0.1",
    "ember-cli-qunit": "0.1.2",
    "ember-cli-simple-auth": "^0.6.7",
    "ember-cli-simple-auth-oauth2": "^0.6.7",
    "ember-data": "^1.0.0-beta.11",
    "ember-data-route": "0.0.3",
    "ember-export-application-global": "^1.0.0",
    "ember-pikaday": "^0.1.0",
    "ember-validations": "^2.0.0-alpha.1",
    "express": "^4.8.5",
    "glob": "^4.0.5"
  },
  "dependencies": {
    "ember-responsive": "^1.0.0",
    "ember-velocity-mixin": "^0.2.0"
  }

bower.json

{
  "name": "myapp",
  "dependencies": {
    "handlebars": "2.0.0",
    "jquery": "^1.11.1",
    "ember": "~1.9.0",
    "ember-data": "1.0.0-beta.11",
    "ember-resolver": "~0.1.11",
    "loader.js": "stefanpenner/loader.js#1.0.1",
    "ember-cli-shims": "stefanpenner/ember-cli-shims#0.0.3",
    "ember-cli-test-loader": "rwjblue/ember-cli-test-loader#0.0.4",
    "ember-load-initializers": "stefanpenner/ember-load-initializers#0.0.2",
    "bootstrap": "~3.2.0",
    "video.js": "~4.8.5",
    "ember-simple-auth": "0.6.7",
    "ember-qunit": "0.1.8",
    "ember-qunit-notifications": "0.0.4",
    "qunit": "~1.15.0",
    "exifreader": "*",
    "pikaday": "~1.2.0",
    "momentjs": "~2.8.3",
    "emojione": "~1.2.4",
    "dom-ruler": "0.1.3",
    "jQuery-linkify": "~1.1.7",
    "FitText.js": "~1.2.0",
    "hammerjs": "~2.0.4",
    "hint.css": "~1.3.3",
    "jquery.inputmask": "~3.1.47",
    "masonry": "~3.2.1",
    "imagesloaded": "~3.1.8",
    "css-element-queries": "~0.0.2"
  },
  "resolutions": {
    "handlebars": "2.0.0"
  }
}

Brocfile.js

/* global require, module */

var EmberApp = require('ember-cli/lib/broccoli/ember-app');

var app = new EmberApp({
  lessOptions: {
    paths: [
      'bower_components/bootstrap/less',
      'bower_components/video.js/dist/video-js'
    ]
  },
  fingerprint: {
    exclude: ['images/avatars', '/images/logo-for-stripe.jpg'],
  }
});

// Use `app.import` to add additional libraries to the generated
// output files.
//
// If you need to use different assets in different
// environments, specify an object as the first parameter. That
// object's keys should be the environment name and the values
// should be the asset to use in that environment.
//
// If the library that you are including contains AMD or ES6
// modules that you would like to import into your application
// please specify an object with the list of modules as keys
// along with the exports of each module as its value.

app.import('bower_components/bootstrap/dist/js/bootstrap.js');
app.import('bower_components/video.js/dist/video-js/video.js');
app.import('bower_components/exifreader/js/ExifReader.js');
app.import('bower_components/emojione/lib/js/emojione.js');
app.import('bower_components/jQuery-linkify/src/linkified.js');
app.import('bower_components/FitText.js/jquery.fittext.js');
app.import('bower_components/hammerjs/hammer.js');
app.import('bower_components/jquery.inputmask/dist/jquery.inputmask.bundle.js');
app.import('bower_components/masonry/dist/masonry.pkgd.js');
app.import('bower_components/imagesloaded/imagesloaded.js');
app.import('bower_components/css-element-queries/src/ResizeSensor.js');
app.import('bower_components/css-element-queries/src/ElementQueries.js');

app.import('bower_components/hint.css/hint.css');

module.exports = app.toTree();
btecu commented 9 years ago

Same thing happened to me, except I updated from 0.1.4. For some reason I thought maps would actually improve on built time.

rwjblue commented 9 years ago

@beerlington - Can you disable sourcemaps (add sourcemaps: { enabled: false } to the EmberApp instantiation in your Brocfile.js) and compare times?

rwjblue commented 9 years ago

I have submitted a few PR's to make the slow tree graph a bit more useful here.

beerlington commented 9 years ago

@rwjblue disabling source maps doesn't seem to have any effect on the build time assuming I'm doing it right:

var app = new EmberApp({
  lessOptions: {
    paths: [
      'bower_components/bootstrap/less',
      'bower_components/video.js/dist/video-js'
    ]
  },
  fingerprint: {
    exclude: ['images/avatars', '/images/logo-for-stripe.jpg'],
  },
  sourcemaps: { enabled: false }
});

If I can find some time during lunch today, I'll post a project that demonstrates the issue. Thanks!

stefanpenner commented 9 years ago

@ef4 you may have some insight

beerlington commented 9 years ago

I created a test app that demonstrates what I'm seeing. All I did was pull over package.json, bower.json, and the Brocfile from my production app. Other than that it's just the default ember init with a new "hello" route.

I also added a branch with v0.1.2 that I used to verify the issue is something between those versions. On my MB Air I'm seeing close to a 8x-10x slowdown with this project (both initial and rebuilds).

rwjblue commented 9 years ago

@beerlington - Thanks for the repro app, I'll try to pull it down and take a look tomorrow.

marcemira commented 9 years ago

The same happened to me after upgrading from 0.1.4 to 0.1.5, rebuild times went from ~500ms to ~7s.. I was on a deadline so didn't had the time to report or check what was going on :/.

stefanpenner commented 9 years ago

I'm pretty sure I know what's the problem. Need to do some exploration to confirm though.

Restuta commented 9 years ago

Same here, with 0.1.4 initial start (ember serve):

Build successful - 1053ms.

Slowest Trees                  | Total
-------------------------------+----------------
EsnextFilter                   | 203ms
SassCompiler                   | 153ms
EsnextFilter                   | 95ms
ES6Concatenator                | 83ms
JSHint - App                   | 69ms
ES3SafeFilter                  | 58ms
Concat                         | 58ms

and new line added to index.html

file changed index.html

Build successful - 237ms.

Slowest Trees                  | Total
-------------------------------+----------------
Concat                         | 18ms
JSHint - Tests                 | 16ms
SassCompiler                   | 15ms
SassCompiler                   | 15ms
TreeMerger (allTrees)          | 12ms

same with 0.1.5


Build successful - 3016ms.

Slowest Trees                  | Total
-------------------------------+----------------
Class                          | 1795ms
EsnextFilter                   | 282ms
SassCompiler                   | 157ms

and

Build successful - 467ms.

Slowest Trees                  | Total
-------------------------------+----------------
Class                          | 120ms
EsnextFilter                   | 33ms
Class                          | 25ms
Funnel                         | 25ms

Almost 100% perf penalty

j15e commented 9 years ago

Same here, the first build time is not much worse, but each subsequent build is 3x slower than with previous version (0.1.2 for us).

salzhrani commented 9 years ago

same here :(

stefanpenner commented 9 years ago

@ef4 got some time?

e00dan commented 9 years ago

Ember-cli@0.1.2 ~36000ms Ember-cli@0.1.7 165370ms

stefanpenner commented 9 years ago

@Kuzirashi that is pretty useless feedback, please provide actionable information.

I suspect your app is quite large, and removing ember-cli-6to5 from package.json and disabling es3 safe will help your build.

We have plans to add more advanced caching to 6to5, as they hope to also improve its performance.

stefanpenner commented 9 years ago

@ef4 I noticed that it seems more files in bower_components/vendor are being processed then expected.

e00dan commented 9 years ago

@stefanpenner I removed "broccoli-sass": "^0.3.3" from devDependencies in package.json, installed "ember-cli-sass": "3.0.3" and now build time decreased from 165370ms to just 11800ms:

$ ember serve
version: 0.1.7
Livereload server on port 35729
Serving on http://0.0.0.0:4200/

Build successful - 12694ms.

Slowest Trees                  | Total          
-------------------------------+----------------
CoffeeScriptFilter             | 4652ms         
Concat: Vendor                 | 2772ms         
ES6Modules                     | 2427ms         

^C
$ ember serve
version: 0.1.7
Livereload server on port 35729
Serving on http://0.0.0.0:4200/

Build successful - 11800ms.

Slowest Trees                  | Total          
-------------------------------+----------------
CoffeeScriptFilter             | 4425ms         
Concat: Vendor                 | 2558ms         
ES6Modules                     | 2064ms

It's even faster than in ember-cli@0.1.2(~30k ms).

stefanpenner commented 9 years ago

@Kuzirashi whats your file count, and what is the time for incremental?

e00dan commented 9 years ago

@stefanpenner

$ git ls-files | wc -l
663

Application directory:

84757 files
size: 564,0 MB

I don't understand what time for incremental means.

j15e commented 9 years ago

@Kuzirashi incremental is when the app recompile partially after a file change (the subsequent builds after the first).

ember-cli-sass depends on brocolli-sass so I doubt this would change anything (I do not see any difference here)

e00dan commented 9 years ago
file changed controllers/application.coffee

Build successful - 2651ms.

Slowest Trees                  | Total          
-------------------------------+----------------
ES6Modules                     | 375ms          
Concat: Vendor                 | 349ms          
SassCompiler                   | 340ms          
Concat: App                    | 336ms          
Funnel: App JS Files           | 145ms          
SourcemapConcat                | 133ms

Ok, my app compiles now faster than ever before so I'm happy.

stefanpenner commented 9 years ago

@kazirashi thanks, that looks reasonable. We did regress some performance when adding source-map support. We will hopefully sort that out soon.

j15e commented 9 years ago

I have disabled source-map generation, but it does have any large impact performance, it is only shaving like 100ms over 1600ms during sequential builds (aka the major issue does not seems to be with the new source map default). A sequential build would take 500-600ms before with ember-cli 1.2.

https://gist.github.com/j15e/83275f0e91c24bf3f711

stefanpenner commented 9 years ago

Instead of posting lots amount of code in this comment thread, please create a demo app demonstrating your stuff. As it is merely noisy and distracting from conversation.

stefanpenner commented 9 years ago

I have disabled source-map generation, but it does have any large impact performance,

yes, the machinery to enable source maps is the regression, not really the source maps themselves. (currently)

Restuta commented 9 years ago

@stefanpenner do you need test app demonstrating perf issues comparing to 0.1.4? It will be almost blank, with just twitter boostrap saas added.

beerlington commented 9 years ago

@Restuta @stefanpenner the test app I posted earlier in the thread should demonstrate the issue pretty well with a blank app.

wayne-o commented 9 years ago

Here are my build times:

Slowest Trees | Total -------------------------------+---------------- CompassCompiler | 17259ms Concat: Vendor | 10991ms Funnel: App JS Files | 9724ms ES6Modules | 9285ms SourcemapConcat | 7077ms SourcemapConcat | 6981ms Concat: Test Support JS | 6387ms Concat: App | 6328ms ES3SafeFilter | 6279ms JSHint - App | 6024ms

really, really slow!

The project being built is here: https://github.com/wayne-o/sonatribe

it runs inside the vagrant box if that matters.

I have also noticed I need to manually trigger a build on file changes - is that normal?

jakecraige commented 9 years ago

@wayne-o I'm getting ~27s builds when running your setup. I also installed watchman, but that only cut off around 2s. It's by no means acceptable but different.

Here's an image with the DEBUG env set. I'm not sure if it will help someone who knows more about the watching but perhaps.

1__tmux

wayne-o commented 9 years ago

I am going to try the following:

On host OSX box: revert back to v0.1.3 update to latest v0.1.7

Then back in vagrant: revert back to v0.1.3 update to latest v0.1.7

I'll post the results back here - I will have to manually upgrade the app though as running ember init inside the project and fixing up the merges resulted in me getting a blank page when the app loaded! no errors (after fixing up the CSP stuff), but no app either...

Can't do the OSX part as my host box is screwy :/

stefanpenner commented 9 years ago

it runs inside the vagrant box if that matters.

what mechanism of file sharing is being used? This is likely a large contributor. If you are on osx, why do you need a VM to work on ember apps? Seems extremely convoluted, when it works on the bare metal.

wayne-o commented 9 years ago

I was using NFS but live rebuild stopped working so ATM it is:

config.vm.synced_folder ".", "/vagrant"

I want it to be easy for other people to get set up and running - vagrant seems to be the best way to do this. Whatever platform they are using.

stefanpenner commented 9 years ago

@wayne-o much time has gone into making ember-cli portable by itself, what can we do to improve that path. Telling people to run a VM to get it working easily, is not acceptable from my point of view.

So what can we do, so that you don't feel the vm offers anything compelling.

Basically the problem is the quirks of shared folders, that i really really want to avoid entirely.

wayne-o commented 9 years ago

I find the issues related to running Node without sudo, and Node on Ubuntu is a nause. ATM I have a strange error on my OSX box pertaining to libsass that I have no clue as to what is causing it and short of re-installing OSX I'm not sure how to get ember-cli running again on it. It's not just that though, it's installing the API and it's deps (mongo, memcached, rabbitmq - whatever they may be). I guess I could just as easily script it to run on OSX (for those who haven't got a bodged node installation) - and have started with that effort but for the guys running on Windows; that's another story all together.

I'm coming over from .NET me through pure lang fatigue and believe - .NET has it's issues! I am loving Node / Ember so far - I just know that if I want others to help me with my little project then it needs to be easy for them. I was basically trying to make the barrier to entry very low.

wayne-o commented 9 years ago

I guess the TL;DR of the above is that it isn't ember-cli that is the barrier :)

topaxi commented 9 years ago

I used vagrant for development (stopped using it though, but it's still nice to easy setup a complete dev-env with database etc. for other developers).

Anyways, as far as I remember, the following sped up the build process a lot.

  config.vm.provision :shell, :run => 'always' do |s|
    s.inline = 'mkdir /tmp/project; chown vagrant:vagrant /tmp/project; mount -o bind /tmp/project /vagrant/tmp'
  end

I stopped using vagrant because the shared folders and build on file changes didn't really work, switching to the polling watcher solved this, but resulted in very high cpu usage...

wayne-o commented 9 years ago

Just FYI

I have managed to get my OSX box to work and have ported my code over to the latest CLI and it's now all working super fast.

I guess it's the vagrant shared folder thing that was causing the problem. Bit of a shame but no bother in the grand scheme of things and certainly no fault of ember-cli :)

stefanpenner commented 9 years ago

I guess it's the vagrant shared folder thing that was causing the problem. Bit of a shame but no bother in the grand scheme of things and certainly no fault of ember-cli :)

i would like to nail that problem someday, but it is a pandoras box'esq problem. Let's aim to make ember-cli as portable as stable as possible, so it can always run "on the metal"

jfcouture commented 9 years ago

Any update on the original issue? My build times just keep climbing. The update to 0.1.5 initially took the build from 2s to 4-5s, but now 2 weeks later, it's taking 12s. Rebuilds went from 500ms to 3s. It doesn't feel like a linear increase compared to the amount of code added in those 2 weeks.

Any way I can help with this issue? Any way to mitigate this in the mean time?

rynam0 commented 9 years ago

FWIW, 0.1.5 was the first version I had tried. I'm on osx yosemite and installed watchman. Almost had to drop embercli as it would hang my box and reminded me of gwt dev mode in terms of speed (or lack thereof). I'm now running ember-cli-ramdisk and am getting instant live reloads with version 0.1.7.

stefanpenner commented 9 years ago

@rynam0 sounds like something is watching your tmpdir, be sure to disable anything that is watching it. (or if it's on some slow disk)

we will slow be moving the tmpdir out of the projects directory, just requires work at the broccoli layer

rynam0 commented 9 years ago

I'm not entirely sure how to determine what might be watching the tmp directory but I'm on a 3yo MBP with a 750 GB SATA Disk. I'm guessing this qualifies as a "slow disk".

stefanpenner commented 9 years ago

@rynam0 which editor are u using, sublime and friends watch the tmpdir, you can easily disable http://www.ember-cli.com/#usage-with-sublime-text

stefanpenner commented 9 years ago

with a 750 GB SATA Disk. I'm guessing this qualifies as a "slow disk".

unsure, i was more referring to something like a USB stick, or even worse an encrypted USB stick, something network attached.

BUt yes the ramdisk will be a breath of fresh air for a HDD user. thanks @machty

rynam0 commented 9 years ago

This isn't editor related as I see the same behavior using a project created and modified on the command line as I do when using an IDE. But to answer your question, I use IntelliJ and exclude node_modules and tmp directories from indexing.

rynam0 commented 9 years ago

I also wanted to thank @machty! My office mate was getting nervous (he will be joining me on my project very soon) when he heard my fan running half the day. Side note: I just ported my ember project from brunch to ember-cli and felt all was lost before i found @machty's package. I did see comments on what was found in the brunch source code and why it wasn't used in ember-cli. I'm ecstatic to be getting instant reloads again. Thanks to all involved in ember-cli in any way... Loving it!

machty commented 9 years ago

Hooray!