2012-08-22 75 views
12

如何在每次頁面重新加載時(無論資產是否被修改)強制資產呈現資產?我目前工作的地方我用Assetic管理和編譯.LESS文件的Symfony2項目如何在每次頁面重新加載時強制資產呈現資產?

關於我的問題的詳細解釋。我有一切工作正常,但我有一個小問題,我想解決。

在config.yml中,我將assetic use_controller設置爲true。

# Assetic Configuration 
assetic: 
debug:   %kernel.debug% 
use_controller: true 

結果是Symfony每次動態呈現新的.css文件時.less文件被修改。這很棒。

我的問題是,我使用的是主project.less文件,我導入所有其他文件.LESS

// Import Twitter Bootstrap 
@import "../../../../../../vendor/twitter/bootstrap/less/bootstrap.less"; 

// Import Foo 
@import "foo.less"; 

... 

它讓我保持一個乾淨的結構,也從供應商導入.LESS文件,例如:twitter引導。

在我的樹枝模板中,我只調用這個主文件。

{% stylesheets '@ProjectWebBundle/Resources/public/less/project.less' filter='less' %} 
     <link rel="stylesheet" type="text/css" media="screen" href="{{ asset_url }}" /> 
{% endstylesheets %}  

由於這個主要的.less文件從不修改,Assetic不會重新編譯資產。這就是爲什麼我希望它能夠在文件被修改或不被修改時渲染文件。

+0

嘗試'{%樣式表 '@ ProjectWebBundle /資源/公/更少/ project.less' 過濾器= '少' 調試=真正%}' – Florent

+0

感謝您的快速答覆@Florent,但它並沒有解決問題。 – Evarouss

回答

0

在完成 修改後,您應該傳遞給use_controller: false並編譯您的資產。

如果你想編譯資產:

php app/console assetic:dump 
+2

它的工作原理。但是這意味着每次修改文件時,都必須執行該命令。這是一個痛苦。 如果我將一個--watch參數添加到命令中,那麼我的問題與上面所述完全相同。 – Evarouss

3

我創建a simple script來解決這個問題。請嘗試一下,讓我知道它是否有幫助。

#!/bin/bash 

# assetic-watch: A very simple shell-script to recursively and efficiently 
# watch for asset changes and to trigger automatic recompilation. 
# 
# By Slava Fomin II <[email protected]> 
# Feel free to contact me. 
# From Russia with Love. 
# Let's make this World a Better place! 
# -------------------------------------- 

#===============# 
# CONFIGURATION # 
#===============# 

# Path relative to "Symfony/src" directory. 
# File changes under specified directory will trigger recompilation 
# of all assets. 
WATCH_PATH="Name/Bundle/NameBundle/Resources/public/css" 

# Environment. 
ENV="dev" 

# Additional options for "app/console". 
OPTS="" 

# inotifywait events to watch for. 
INW_EVENTS="close_write,moved_to,create" 

# Optional inotifywait arguments. 
INW_OPTS="" 

# Relative path to the Symfony root directory. 
SYMFONY_PATH="../" 

#============# 
# PROCESSING # 
#============# 

SCRIPT_DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)" 
CONSOLE_PATH="$SCRIPT_DIR/${SYMFONY_PATH}/app/console" 
SRC_PATH="$SCRIPT_DIR/${SYMFONY_PATH}/src/$WATCH_PATH" 

quietly() { "[email protected]" > /dev/null 2>&1; } 

while true; do 
    quietly inotifywait --recursive -e $INW_EVENTS $INW_OPTS $SRC_PATH 
    php $CONSOLE_PATH assetic:dump --env=$ENV $OPTS 
done 

我真的希望Symfony的開發商將在Assetic束的未來版本中解決這個問題。我認爲這是一個嚴重的限制。

+0

我不能夠感謝你。上次我嘗試過這種方式,它並沒有爲我工作,但現在我的環境。有點不同。這是迄今爲止唯一的解決方案,它使用live.js自動刷新@imported的CSS。謝謝一堆!我花了太多的時間尋找解決方案,我想我會回到你身邊,因爲我知道你的劇本很有趣。它終於得到了回報:-) – blamb

+0

哦,謝謝@BrianThomas,我很樂意幫助=)我不再使用資產,我切換到Grunt,現在轉向Gulp,自動編譯我的所有腳本。這是管理資產的一種非常靈活和強大的方式。你甚至可以使用livereload。 –

+0

我同意,這是一個非常合理的事情。請隨時編輯我的答案並添加代碼示例。 –

10

AFAIK有這個沒有完美的解決方案尚未

我用:

php app/console assetic:dump --watch 

這將編譯.LESS每次檢測到任何引用的.LESS文件的改變文件時間你的模板。

強制編譯你必須在你的「主」文件(@輸入其他文件)中做任何改變。但是,好消息是,這足以「觸摸」文件來做到這一點。所以,你可以手動觸摸它每次你需要:

touch ~/web/css/main.less; 

或者,我最常做的是建立觸及這個「主」文件各60秒左右的腳本:

while true; do 
    sleep 60 
    touch ~/web/css/main.less 
done 

這應該在linux和mac上工作。

希望它有幫助。至少暫時:)

11

我使用的是緩存文件的Assetic的Lessphp過濾器。至於我自己,我已經創建了一個擴展默認Assetic的過濾器,觸動每一個文件與當前時間

<?php 

namespace Xxx\AssetsBundle\Assetic\Filter; 

use Assetic\Asset\AssetInterface; 
use Assetic\Filter\LessphpFilter; 

class LessphpNonCachedFilter extends LessphpFilter 
{ 
    public function filterLoad(AssetInterface $asset) 
    { 
     $root = $asset->getSourceRoot(); 
     $path = $asset->getSourcePath(); 

     $filename = realpath($root . '/' . $path); 

     if (file_exists($filename)) { 
      touch($filename); 
     } 

     parent::filterLoad($asset); 
    } 
} 

並且必須設置在參數節(services.yml)「assetic.filter.lessphp.class」一類:

parameters: 
    assetic.filter.lessphp.class: Xxx\AssetsBundle\Assetic\Filter\LessphpNonCachedFilter 
+0

注意:touch需要寫入權限。您需要確保您的'project.less'文件具有設置的xx6權限。 (我把我的地址設置爲0666.) – Kevin

+0

對我不起作用(symfony 2.1.2) – timaschew

+0

我通過'node'使用'LESS','touch'原理保持不變,'touch'文件'(例如:bootstrap.less)''在你的控制器'__construct()' - 它會強制重新編譯每個頁面加載 – Anil