Skip to content

Commit 2e1ef38

Browse files
committed
Merge pull request #164 from solcre/bugfix/duplicate-filters
Bugfix/duplicate filters
2 parents eb16d2e + 4e73e28 commit 2e1ef38

File tree

4 files changed

+114
-3
lines changed

4 files changed

+114
-3
lines changed

src/AssetManager/Service/AssetFilterManager.php

Lines changed: 11 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -25,7 +25,12 @@ class AssetFilterManager implements ServiceLocatorAwareInterface, MimeResolverAw
2525
* @var MimeResolver
2626
*/
2727
protected $mimeResolver;
28-
28+
29+
/**
30+
* @var FilterInterface[] Filters already instantiated
31+
*/
32+
protected $filterInstances = array();
33+
2934
/**
3035
* Construct the AssetFilterManager
3136
*
@@ -145,7 +150,11 @@ protected function ensureByFilter(AssetInterface $asset, $filter)
145150
);
146151
}
147152

148-
$filterInstance = new $filterClass;
153+
if (!isset($this->filterInstances[$filterClass])) {
154+
$this->filterInstances[$filterClass] = new $filterClass();
155+
}
156+
157+
$filterInstance = $this->filterInstances[$filterClass];
149158

150159
$asset->ensureFilter($filterInstance);
151160
}

tests/AssetManagerTest/Service/AssetFilterManagerTest.php

Lines changed: 28 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -3,6 +3,7 @@
33
namespace AssetManagerTest\Service;
44

55
use Assetic\Asset\StringAsset;
6+
use Assetic\Filter\FilterInterface;
67
use PHPUnit_Framework_TestCase;
78
use AssetManager\Service\AssetFilterManager;
89
use Zend\ServiceManager\ServiceManager;
@@ -93,4 +94,31 @@ public function testensureByInvalid()
9394

9495
$assetFilterManager->setFilters('test/path.test', $asset);
9596
}
97+
98+
public function testFiltersAreInstantiatedOnce()
99+
{
100+
$assetFilterManager = new AssetFilterManager(array(
101+
'test/path.test' => array(
102+
array(
103+
'filter' => 'CustomFilter'
104+
),
105+
),
106+
));
107+
108+
$filterInstance = null;
109+
110+
$asset = $this->getMock('Assetic\Asset\AssetInterface');
111+
$asset
112+
->expects($this->any())
113+
->method('ensureFilter')
114+
->with($this->callback(function (FilterInterface $filter) use (&$filterInstance) {
115+
if ($filterInstance === null) {
116+
$filterInstance = $filter;
117+
}
118+
return $filter === $filterInstance;
119+
}));
120+
121+
$assetFilterManager->setFilters('test/path.test', $asset);
122+
$assetFilterManager->setFilters('test/path.test', $asset);
123+
}
96124
}

tests/AssetManagerTest/Service/AssetManagerTest.php

Lines changed: 56 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -9,6 +9,8 @@
99
use AssetManager\Cache\FilePathCache;
1010
use AssetManager\Service\AssetManager;
1111
use AssetManager\Service\MimeResolver;
12+
use AssetManager\Resolver\CollectionResolver;
13+
use AssetManager\Resolver\AggregateResolver;
1214
use Zend\Http\Response;
1315
use Zend\Http\PhpEnvironment\Request;
1416
use Zend\Console\Request as ConsoleRequest;
@@ -23,6 +25,7 @@ public function setUp()
2325
require_once __DIR__ . '/../../_files/JSMin.inc';
2426
require_once __DIR__ . '/../../_files/CustomFilter.php';
2527
require_once __DIR__ . '/../../_files/BrokenFilter.php';
28+
require_once __DIR__ . '/../../_files/ReverseFilter.php';
2629
}
2730

2831
protected function getRequest()
@@ -54,6 +57,24 @@ protected function getResolver($resolveTo = __FILE__)
5457
return $resolver;
5558
}
5659

60+
public function getCollectionResolver()
61+
{
62+
$aggregateResolver = new AggregateResolver;
63+
$mockedResolver = $this->getResolver(__DIR__ . '/../../_files/require-jquery.js');
64+
$collArr = array(
65+
'blah.js' => array(
66+
'asset-path'
67+
)
68+
);
69+
$resolver = new CollectionResolver($collArr);
70+
$resolver->setAggregateResolver($aggregateResolver);
71+
72+
$aggregateResolver->attach($mockedResolver, 500);
73+
$aggregateResolver->attach($resolver, 1000);
74+
75+
return $resolver;
76+
}
77+
5778
public function testConstruct()
5879
{
5980
$resolver = $this->getMock('AssetManager\Resolver\ResolverInterface');
@@ -209,6 +230,41 @@ public function testSetExtensionFilters()
209230
$this->assertEquals($minified, $response->getBody());
210231
}
211232

233+
public function testSetExtensionFiltersNotDuplicate()
234+
{
235+
$config = array(
236+
'filters' => array(
237+
'js' => array(
238+
array(
239+
'filter' => '\ReverseFilter',
240+
),
241+
),
242+
),
243+
);
244+
245+
$resolver = $this->getCollectionResolver();
246+
$assetFilterManager = new AssetFilterManager($config['filters']);
247+
$mimeResolver = new MimeResolver;
248+
$assetFilterManager->setMimeResolver($mimeResolver);
249+
$resolver->setAssetFilterManager($assetFilterManager);
250+
251+
$response = new Response;
252+
$request = $this->getRequest();
253+
// Have to change uri because asset-path would cause an infinite loop
254+
$request->setUri('http://localhost/base-path/blah.js');
255+
256+
$assetCacheManager = $this->getAssetCacheManagerMock();
257+
$assetManager = new AssetManager($resolver->getAggregateResolver(), $config);
258+
$assetManager->setAssetCacheManager($assetCacheManager);
259+
$assetManager->setAssetFilterManager($assetFilterManager);
260+
261+
$this->assertTrue($assetManager->resolvesToAsset($request));
262+
$assetManager->setAssetOnResponse($response);
263+
264+
$reversedOnlyOnce = '1' . strrev(file_get_contents(__DIR__ . '/../../_files/require-jquery.js'));
265+
$this->assertEquals($reversedOnlyOnce, $response->getBody());
266+
}
267+
212268
public function testSetMimeTypeFilters()
213269
{
214270
$config = array(
@@ -323,7 +379,6 @@ public function testSetFalseClassFilter()
323379

324380
public function testSetAssetOnResponse()
325381
{
326-
327382
$assetFilterManager = new AssetFilterManager();
328383
$assetCacheManager = $this->getAssetCacheManagerMock();
329384
$mimeResolver = new MimeResolver;

tests/_files/ReverseFilter.php

Lines changed: 19 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,19 @@
1+
<?php
2+
3+
4+
use Assetic\Asset\AssetInterface;
5+
6+
class ReverseFilter implements Assetic\Filter\FilterInterface
7+
{
8+
private static $executed;
9+
public function filterLoad(AssetInterface $asset)
10+
{
11+
}
12+
13+
public function filterDump(AssetInterface $asset)
14+
{
15+
self::$executed++;
16+
$content = $asset->getContent();
17+
$asset->setContent(self::$executed . strrev($content));
18+
}
19+
}

0 commit comments

Comments
 (0)