vendor/assetic/src/Assetic/Asset/AssetCollection.php
author ymh <ymh.work@gmail.com>
Sun, 06 Nov 2011 23:44:37 +0100
changeset 27 1df556b2c0f9
parent 0 7f95f8617b0b
permissions -rwxr-xr-x
Correct memory problem
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
0
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
     1
<?php
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
     2
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
     3
/*
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
     4
 * This file is part of the Assetic package, an OpenSky project.
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
     5
 *
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
     6
 * (c) 2010-2011 OpenSky Project Inc
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
     7
 *
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
     8
 * For the full copyright and license information, please view the LICENSE
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
     9
 * file that was distributed with this source code.
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
    10
 */
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
    11
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
    12
namespace Assetic\Asset;
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
    13
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
    14
use Assetic\Filter\FilterCollection;
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
    15
use Assetic\Filter\FilterInterface;
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
    16
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
    17
/**
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
    18
 * A collection of assets.
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
    19
 *
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
    20
 * @author Kris Wallsmith <kris.wallsmith@gmail.com>
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
    21
 */
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
    22
class AssetCollection implements AssetInterface, \IteratorAggregate
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
    23
{
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
    24
    private $assets;
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
    25
    private $filters;
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
    26
    private $sourceRoot;
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
    27
    private $targetPath;
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
    28
    private $content;
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
    29
    private $clones;
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
    30
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
    31
    /**
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
    32
     * Constructor.
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
    33
     *
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
    34
     * @param array  $assets     Assets for the current collection
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
    35
     * @param array  $filters    Filters for the current collection
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
    36
     * @param string $sourceRoot The root directory
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
    37
     */
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
    38
    public function __construct($assets = array(), $filters = array(), $sourceRoot = null)
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
    39
    {
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
    40
        $this->assets = array();
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
    41
        foreach ($assets as $asset) {
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
    42
            $this->add($asset);
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
    43
        }
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
    44
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
    45
        $this->filters = new FilterCollection($filters);
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
    46
        $this->sourceRoot = $sourceRoot;
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
    47
        $this->clones = new \SplObjectStorage();
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
    48
    }
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
    49
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
    50
    /**
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
    51
     * Adds an asset to the current collection.
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
    52
     *
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
    53
     * @param AssetInterface $asset An asset
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
    54
     */
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
    55
    public function add(AssetInterface $asset)
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
    56
    {
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
    57
        $this->assets[] = $asset;
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
    58
    }
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
    59
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
    60
    public function all()
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
    61
    {
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
    62
        return $this->assets;
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
    63
    }
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
    64
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
    65
    public function ensureFilter(FilterInterface $filter)
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
    66
    {
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
    67
        $this->filters->ensure($filter);
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
    68
    }
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
    69
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
    70
    public function getFilters()
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
    71
    {
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
    72
        return $this->filters->all();
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
    73
    }
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
    74
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
    75
    public function clearFilters()
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
    76
    {
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
    77
        $this->filters->clear();
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
    78
    }
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
    79
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
    80
    public function load(FilterInterface $additionalFilter = null)
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
    81
    {
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
    82
        // loop through leaves and load each asset
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
    83
        $parts = array();
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
    84
        foreach ($this as $asset) {
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
    85
            $asset->load($additionalFilter);
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
    86
            $parts[] = $asset->getContent();
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
    87
        }
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
    88
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
    89
        $this->content = implode("\n", $parts);
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
    90
    }
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
    91
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
    92
    public function dump(FilterInterface $additionalFilter = null)
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
    93
    {
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
    94
        // loop through leaves and dump each asset
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
    95
        $parts = array();
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
    96
        foreach ($this as $asset) {
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
    97
            $parts[] = $asset->dump($additionalFilter);
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
    98
        }
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
    99
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   100
        return implode("\n", $parts);
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   101
    }
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   102
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   103
    public function getContent()
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   104
    {
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   105
        return $this->content;
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   106
    }
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   107
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   108
    public function setContent($content)
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   109
    {
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   110
        $this->content = $content;
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   111
    }
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   112
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   113
    public function getSourceRoot()
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   114
    {
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   115
        return $this->sourceRoot;
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   116
    }
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   117
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   118
    public function getSourcePath()
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   119
    {
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   120
    }
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   121
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   122
    public function getTargetPath()
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   123
    {
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   124
        return $this->targetPath;
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   125
    }
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   126
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   127
    public function setTargetPath($targetPath)
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   128
    {
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   129
        $this->targetPath = $targetPath;
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   130
    }
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   131
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   132
    /**
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   133
     * Returns the highest last-modified value of all assets in the current collection.
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   134
     *
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   135
     * @return integer|null A UNIX timestamp
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   136
     */
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   137
    public function getLastModified()
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   138
    {
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   139
        if (!count($this->assets)) {
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   140
            return;
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   141
        }
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   142
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   143
        $mapper = function (AssetInterface $asset)
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   144
        {
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   145
            return $asset->getLastModified();
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   146
        };
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   147
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   148
        return max(array_map($mapper, $this->assets));
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   149
    }
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   150
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   151
    /**
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   152
     * Returns an iterator for looping recursively over unique leaves.
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   153
     */
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   154
    public function getIterator()
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   155
    {
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   156
        return new \RecursiveIteratorIterator(new AssetCollectionFilterIterator(new AssetCollectionIterator($this, $this->clones)));
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   157
    }
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   158
}
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   159
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   160
/**
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   161
 * Asset collection filter iterator.
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   162
 *
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   163
 * The filter iterator is responsible for de-duplication of leaf assets based
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   164
 * on both strict equality and source URL.
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   165
 *
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   166
 * @author Kris Wallsmith <kris.wallsmith@gmail.com>
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   167
 * @access private
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   168
 */
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   169
class AssetCollectionFilterIterator extends \RecursiveFilterIterator
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   170
{
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   171
    private $visited;
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   172
    private $sources;
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   173
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   174
    /**
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   175
     * Constructor.
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   176
     *
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   177
     * @param AssetCollectionIterator $iterator The inner iterator
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   178
     * @param array                   $visited  An array of visited asset objects
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   179
     * @param array                   $sources  An array of visited source strings
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   180
     */
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   181
    public function __construct(AssetCollectionIterator $iterator, array $visited = array(), array $sources = array())
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   182
    {
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   183
        parent::__construct($iterator);
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   184
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   185
        $this->visited = $visited;
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   186
        $this->sources = $sources;
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   187
    }
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   188
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   189
    /**
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   190
     * Determines whether the current asset is a duplicate.
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   191
     *
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   192
     * De-duplication is performed based on either strict equality or by
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   193
     * matching sources.
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   194
     *
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   195
     * @return Boolean Returns true if we have not seen this asset yet
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   196
     */
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   197
    public function accept()
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   198
    {
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   199
        $asset = $this->getInnerIterator()->current(true);
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   200
        $duplicate = false;
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   201
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   202
        // check strict equality
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   203
        if (in_array($asset, $this->visited, true)) {
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   204
            $duplicate = true;
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   205
        } else {
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   206
            $this->visited[] = $asset;
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   207
        }
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   208
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   209
        // check source
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   210
        $sourceRoot = $asset->getSourceRoot();
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   211
        $sourcePath = $asset->getSourcePath();
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   212
        if ($sourceRoot && $sourcePath) {
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   213
            $source = $sourceRoot.'/'.$sourcePath;
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   214
            if (in_array($source, $this->sources)) {
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   215
                $duplicate = true;
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   216
            } else {
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   217
                $this->sources[] = $source;
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   218
            }
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   219
        }
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   220
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   221
        return !$duplicate;
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   222
    }
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   223
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   224
    /**
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   225
     * Passes visited objects and source URLs to the child iterator.
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   226
     */
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   227
    public function getChildren()
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   228
    {
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   229
        return new self($this->getInnerIterator()->getChildren(), $this->visited, $this->sources);
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   230
    }
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   231
}
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   232
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   233
/**
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   234
 * Iterates over an asset collection.
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   235
 *
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   236
 * The iterator is responsible for cascading filters and target URL patterns
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   237
 * from parent to child assets.
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   238
 *
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   239
 * @author Kris Wallsmith <kris.wallsmith@gmail.com>
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   240
 * @access private
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   241
 */
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   242
class AssetCollectionIterator implements \RecursiveIterator
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   243
{
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   244
    private $assets;
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   245
    private $filters;
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   246
    private $output;
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   247
    private $clones;
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   248
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   249
    public function __construct(AssetCollection $coll, \SplObjectStorage $clones)
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   250
    {
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   251
        $this->assets  = $coll->all();
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   252
        $this->filters = $coll->getFilters();
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   253
        $this->output  = $coll->getTargetPath();
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   254
        $this->clones  = $clones;
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   255
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   256
        if (false === $pos = strpos($this->output, '.')) {
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   257
            $this->output .= '_*';
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   258
        } else {
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   259
            $this->output = substr($this->output, 0, $pos).'_*'.substr($this->output, $pos);
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   260
        }
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   261
    }
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   262
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   263
    /**
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   264
     * Returns a copy of the current asset with filters and a target URL applied.
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   265
     *
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   266
     * @param Boolean $raw Returns the unmodified asset if true
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   267
     */
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   268
    public function current($raw = false)
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   269
    {
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   270
        $asset = current($this->assets);
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   271
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   272
        if ($raw) {
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   273
            return $asset;
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   274
        }
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   275
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   276
        // clone once
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   277
        if (!isset($this->clones[$asset])) {
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   278
            $clone = $this->clones[$asset] = clone $asset;
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   279
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   280
            // generate a target path based on asset name
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   281
            $name = sprintf('%s_%d', pathinfo($asset->getSourcePath(), PATHINFO_FILENAME) ?: 'part', $this->key() + 1);
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   282
            $clone->setTargetPath(str_replace('*', $name, $this->output));
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   283
        } else {
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   284
            $clone = $this->clones[$asset];
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   285
        }
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   286
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   287
        // cascade filters
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   288
        foreach ($this->filters as $filter) {
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   289
            $clone->ensureFilter($filter);
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   290
        }
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   291
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   292
        return $clone;
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   293
    }
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   294
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   295
    public function key()
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   296
    {
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   297
        return key($this->assets);
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   298
    }
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   299
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   300
    public function next()
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   301
    {
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   302
        return next($this->assets);
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   303
    }
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   304
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   305
    public function rewind()
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   306
    {
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   307
        return reset($this->assets);
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   308
    }
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   309
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   310
    public function valid()
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   311
    {
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   312
        return false !== current($this->assets);
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   313
    }
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   314
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   315
    public function hasChildren()
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   316
    {
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   317
        return current($this->assets) instanceof AssetCollection;
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   318
    }
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   319
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   320
    /**
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   321
     * @uses current()
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   322
     */
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   323
    public function getChildren()
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   324
    {
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   325
        return new self($this->current(), $this->clones);
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   326
    }
7f95f8617b0b first commit
ymh <ymh.work@gmail.com>
parents:
diff changeset
   327
}