Skip to content

Instantly share code, notes, and snippets.

@ajshort
Created February 17, 2011 04:42
Show Gist options
  • Select an option

  • Save ajshort/830992 to your computer and use it in GitHub Desktop.

Select an option

Save ajshort/830992 to your computer and use it in GitHub Desktop.
ManifestFileFinder.php
<?php
/**
*
*
* @package sapphire
* @subpackage manifest
*/
class ManifestFileFinder {
const CONFIG_FILE = '_config.php';
const EXCLUDE_FILE = '_manifest_exclude';
public static $vcs_dirs = array(
'.git', '.svn', '_svn', '.hg', '.bzr', 'CVS'
);
protected $base;
protected $cache;
protected $options = array(
'name_regex' => null,
'require_config' => true,
'ignore_vcs' => true,
'ignore_excluded' => true,
'ignore_dirs' => array(),
'ignore_top_dirs' => array(),
'ignore_files' => array(),
'flush' => false,
'cache' => true,
'return' => true,
'callback' => null
);
/**
* @param string $base
*/
public function __construct($base) {
$this->base = $base;
$this->cache = SS_Cache::factory(__CLASS__, 'Core', array(
'automatic_serialization' => true,
'lifetime' => null
));
}
/**
* @return string
*/
public function getBase() {
return $this->base;
}
/**
* @return string
*/
public function getCacheKey() {
return md5($this->base . serialize($this->options));
}
/**
* Set an option on this finder instance.
*
* @param string $name
* @param mixed $value
*/
public function setOption($name, $value) {
if (!array_key_exists($name, $this->options)) {
throw new InvalidArgumentException("The option $name doesn't exist.");
}
$this->options[$name] = $value;
}
/**
* @param array $options
*/
public function setOptions(array $options) {
foreach ($options as $k => $v) $this->setOption($k, $v);
}
/**
* @param string $name
* @return mixed
*/
public function getOption($name) {
if (!array_key_exists($name, $this->options)) {
throw new InvalidArgumentException("The option $name doesn't exist.");
}
return $this->options[$name];
}
/**
* @return array
*/
public function find() {
// First look up a cached result if we have one.
if ($this->getOption('cache') && !$this->getOption('flush')) {
if ($found = $this->cache->load($this->getCacheKey())) {
return $found;
}
}
$found = array();
$paths = array();
$return = $this->getOption('return');
$isTop = true;
$ignoreDirs = $this->getOption('ignore_dirs');
$ignoreTopDirs = $this->getOption('ignore_top_dirs');
$ignoreVcs = $this->getOption('ignore_vcs');
$ignoreExcl = $this->getOption('ignore_excluded');
$ignoreFiles = $this->getOption('ignore_files');
$nameRegex = $this->getOption('name_regex');
$callback = $this->getOption('callback');
if ($this->getOption('require_config')) {
foreach (scandir($this->base) as $module) {
if (file_exists("{$this->base}/$module/" . self::CONFIG_FILE)) {
$paths[] = $this->base . '/' . $module;
}
}
} else {
$paths[] = $this->base;
}
while ($pathname = array_pop($paths)) {
foreach (scandir($pathname) as $basename) {
if ($basename == '.' || $basename == '..') {
continue;
}
if (is_dir("$pathname/$basename")) {
if (in_array($basename, $ignoreDirs)) {
continue;
}
if ($isTop && in_array($basename, $ignoreTopDirs)) {
continue;
}
if ($ignoreVcs && in_array($basename, self::$vcs_dirs)) {
continue;
}
if ($ignoreExcl) {
if (file_exists("$pathname/$basename/" . self::EXCLUDE_FILE)) {
continue;
}
}
$paths[] = "$pathname/$basename";
} else {
if (in_array($basename, $ignoreFiles)) {
continue;
}
if ($nameRegex && !preg_match($nameRegex, $basename)) {
continue;
}
if ($callback) {
call_user_func($callback, $basename, "$pathname/$basename");
}
if ($return) $found[] = "$pathname/$basename";
}
}
$isTop = false;
}
// Save the files list if configured to do so.
if ($this->getOption('cache')) {
$this->cache->save($found, $this->getCacheKey());
}
if ($return) return $found;
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment