Last active
August 29, 2015 14:18
-
-
Save lyrixx/069338117ec7d48d6272 to your computer and use it in GitHub Desktop.
VersionCalculator
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
<?php | |
namespace SensioLabs\Toolkit\Assets; | |
use Assetic\AssetManager; | |
use Assetic\Asset\AssetCollection; | |
use Symfony\Component\Finder\Finder; | |
class VersionCalculator | |
{ | |
private $rootDir; | |
private $assetsFolders; | |
private $asseticEnabled; | |
private $am; | |
private $debug; | |
private $extensions; | |
private $ignoredPaths; | |
public function __construct($rootDir, array $assetsFolders = array(), $asseticEnabled = true, AssetManager $am = null) | |
{ | |
$this->rootDir = $rootDir; | |
$this->assetsFolders = $assetsFolders; | |
$this->asseticEnabled = $asseticEnabled; | |
$this->am = $am; | |
// We do no want to use symfony-env and/or symfony-debug | |
// Because this debug mode, is present only for hard-core debug ;) | |
$this->debug = '1' === getenv('SLT_AV_DEBUG'); | |
$this->extensions = array( | |
'js', 'coffee', | |
'css', 'less', | |
'ttf', 'woff', | |
'png', 'jpg', | |
'ico', | |
'swf', | |
); | |
$this->ignoredPaths = array( | |
'\/test\/', '\/tests\/', | |
'\/fixture\/', '\/fixtures\/', | |
'\/vendor\/', '\/vendors\/', | |
'\/example\/', '\/examples\/', | |
'\/sample\/', '\/samples\/', | |
'\/doc\/', '\/docs\/', | |
); | |
} | |
public function addCustomExtension($extension) | |
{ | |
if (!isset($extension[0]) || '.' === $extension[0]) { | |
throw new \InvalidArgumentException('"%s" is not a valid extension', $extension); | |
} | |
$this->extensions[] = $extension; | |
return $this; | |
} | |
public function removeExtension($extension) | |
{ | |
if (!in_array($extension, $this->extensions)) { | |
return false; | |
} | |
$this->extensions = array_filter($this->extensions, function ($v) use ($extension) { | |
return $v !== $extension; | |
}); | |
return true; | |
} | |
public function addCustomIgnoredPath($path) | |
{ | |
$this->ignoredPaths[] = $path; | |
return $this; | |
} | |
public function removeIgnoredPath($path) | |
{ | |
if (!in_array($path, $this->ignoredPaths)) { | |
return false; | |
} | |
$this->ignoredPaths = array_filter($this->ignoredPaths, function ($v) use ($path) { | |
return $v !== $path; | |
}); | |
return true; | |
} | |
public function computeAssetsVersion() | |
{ | |
$hashContext = hash_init('sha1'); | |
if ($this->asseticEnabled) { | |
$this->computeAsseticVersion($hashContext); | |
} | |
if ($this->assetsFolders) { | |
$this->computeStandaloneAssetVersion($hashContext, $this->assetsFolders); | |
} | |
// Always prepend a `v` to avoid side effects (string casted to int) with | |
// this kind of version 811486e356 (=> INF) | |
return 'v'.substr(hash_final($hashContext), 0, 10); | |
} | |
private function computeAsseticVersion($hashContext) | |
{ | |
$names = $this->am->getNames(); | |
sort($names); | |
foreach ($names as $name) { | |
$asset = $this->am->get($name); | |
if (!$asset instanceof AssetCollection) { | |
throw new \LogicException(sprintf('This command can not handle asset of type "%s"', get_class($asset))); | |
} | |
foreach ($asset as $item) { | |
$file = sprintf('%s/%s', $item->getSourceRoot(), $item->getSourcePath()); | |
hash_update_file($hashContext, $file); | |
if ($this->debug) { | |
echo sprintf("%s: %s\n", $file, md5_file($file)); | |
} | |
} | |
} | |
} | |
private function computeStandaloneAssetVersion($hashContext, array $folders = array()) | |
{ | |
if (!is_dir($this->rootDir.'/../web/bundles/')) { | |
throw new \LogicException('You should install asset before running this command (app/console assets:install)'); | |
} | |
$finder = Finder::create()->useBestAdapter()->sortByName()->files(); | |
foreach ($this->ignoredPaths as $path) { | |
$finder->notPath($path); | |
} | |
foreach ($this->extensions as $extension) { | |
$finder->name(sprintf('*.%s', $extension)); | |
} | |
foreach ($folders as $folder) { | |
if (!is_dir($folder) && !glob($folder)) { | |
continue; | |
} | |
$finder->in($folder); | |
} | |
foreach ($finder as $file) { | |
hash_update_file($hashContext, $file); | |
if ($this->debug) { | |
echo sprintf("%s: %s\n", $file, md5_file($file)); | |
} | |
} | |
} | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment