symfonyassetic

Symfony2 Assetic Don't Generate Composite File on --env=dev


Is there any way to tell the Assetic command-line file to not generate the composite "output" file when it builds for the dev environment?

We have it running with the --watch configuration. We have composite files which take a long time to generate and aren't used, so it's a serious waste of time. It also causes it to regenerate all files in that stack, instead of the one single one that changes.

Any ideas? If there isn't, I'm half-tempted to override the asset:dump command myself because we're seriously wasting 1-3 minutes every time we make a tiny file change. =(


Symfony version: 2.2.0 (according to debug bar, just ran Composer update with no changes)

config.yml (assetic block)

assetic:
  debug:          %kernel.debug%
  use_controller: false
  #bundles: []
  #java: /usr/bin/java
  filters:
    cssrewrite: ~
    less:
      node: /usr/bin/node
      node_paths: [/usr/local/lib/node_modules,/usr/lib/node_modules]
      apply_to: "\.less"
    typescript:
      resource: %kernel.root_dir%/../src/GamePlan/Bundle/CoreBundle/Resources/config/assetic.typescript.xml
      apply_to: "\.ts"
      tsc: /usr/local/bin/tsc
      node: /usr/bin/node
      useOut: false

(Custom TypeScriptFilter, but it is happening to CSS files as well, so it shouldn't be that which is causing it... it's also a relatively minor tweak to the one in the official repo.)

config_dev.yml (assetic block)

assetic:
  use_controller: false

Example usage:

{% stylesheets output="bundles/mybundle/styles/mystyle.css"
    filter="cssrewrite"
    "@MyBundle/Resources/styles/a.less"
    "@MyBundle/Resources/styles/b.less"
    "@MyBundle/Resources/styles/subfolder/*.less"
    "@MyBundle/Resources/styles/subfolder/*/*.less"
%}
<link type="text/css" rel="stylesheet" href="{{ asset_url }}"/>
{% endstylesheets %}

Running command (from /var/www as www-data):

php Symfony/app/console assetic:dump --env=dev [--watch]

With or without --watch doesn't change what files are generated, just if it does them all or just watches.

Note sure if this will give anyone a clue as to what is going on, but it tries to generate the composite file before it generates the individual dev ones.

I've also ensured I'm not duplicating any includes, referencing any composite files in other blocks, etc.

It isn't loading the composite files in the HTML, but I can see them generated from the command.

If any more info is needed, please let me know. Thanks.


Solution

  • So I ended up going through the DumpCommand for the Assetic bundle. It turns out they are always unconditionally generated, regardless of environment (there is only a conditional to only do the dev ones if we are in debug mode).

    To fix it myself, I just copied that DumpCommand and made my own version which I ended up adding a condition to the above so it only does it if the environment is prod. I also made it so it'll only dump the dev files if that file has changed.

    This solution isn't perfect and requires paying attention (for example, if one file depends on another, it won't get recompiled so I have to run the original still from time to time if I have a compiler error). However, it works for me.

    The modified dumpAsset() looks like this:

    private function dumpAsset($name, OutputInterface $output)
    {
        $asset = $this->am->get($name);
        $formula = $this->am->getFormula($name);
    
        if (!$this->am->isDebug()) {
            // start by dumping the main asset
            $this->doDump($asset, $output);
        }
    
        // dump each leaf if debug
        if (isset($formula[2]['debug']) ? $formula[2]['debug'] : $this->am->isDebug()) {
            foreach ($asset as $leaf) {
                $mtime = filemtime(($leaf->getSourceRoot() ? $leaf->getSourceRoot() . DIRECTORY_SEPARATOR : '') . $leaf->getSourcePath());
                if ($mtime >= $asset->getLastModified()) {
                    $this->doDump($leaf, $output);
                }
            }
        }
    }