function run_freeze($task, $args)
{
    // check that the symfony librairies are not already freeze for this project
    if (is_readable(sfConfig::get('sf_lib_dir') . '/symfony')) {
        throw new Exception('You can only freeze when lib/symfony is empty.');
    }
    if (is_readable(sfConfig::get('sf_data_dir') . '/symfony')) {
        throw new Exception('You can only freeze when data/symfony is empty.');
    }
    if (is_readable(sfConfig::get('sf_web_dir') . '/sf')) {
        throw new Exception('You can only freeze when web/sf is empty.');
    }
    if (is_link(sfConfig::get('sf_web_dir') . '/sf')) {
        pake_remove(sfConfig::get('sf_web_dir') . '/sf', '');
    }
    $symfony_lib_dir = sfConfig::get('sf_symfony_lib_dir');
    $symfony_data_dir = sfConfig::get('sf_symfony_data_dir');
    pake_echo_action('freeze', 'freezing lib found in "' . $symfony_lib_dir . '"');
    pake_echo_action('freeze', 'freezing data found in "' . $symfony_data_dir . '"');
    pake_mkdirs(sfConfig::get('sf_lib_dir') . DIRECTORY_SEPARATOR . 'symfony');
    pake_mkdirs(sfConfig::get('sf_data_dir') . DIRECTORY_SEPARATOR . 'symfony');
    $finder = pakeFinder::type('any')->ignore_version_control();
    pake_mirror($finder, $symfony_lib_dir, sfConfig::get('sf_lib_dir') . '/symfony');
    pake_mirror($finder, $symfony_data_dir, sfConfig::get('sf_data_dir') . '/symfony');
    pake_rename(sfConfig::get('sf_data_dir') . '/symfony/web/sf', sfConfig::get('sf_web_dir') . '/sf');
    // change symfony paths in config/config.php
    file_put_contents('config/config.php.bak', "{$symfony_lib_dir}#{$symfony_data_dir}");
    _change_symfony_dirs("dirname(__FILE__).'/../lib/symfony'", "dirname(__FILE__).'/../data/symfony'");
    // install the command line
    pake_copy($symfony_data_dir . '/bin/symfony.php', 'symfony.php');
}
Пример #2
0
function run_propel_generate_crud($task, $args)
{
    if (count($args) < 2) {
        throw new Exception('You must provide your module name.');
    }
    if (count($args) < 3) {
        throw new Exception('You must provide your model class name.');
    }
    $theme = isset($args[3]) ? $args[3] : 'default';
    $app = $args[0];
    $module = $args[1];
    $model_class = $args[2];
    $sf_root_dir = sfConfig::get('sf_root_dir');
    // generate module
    $tmp_dir = $sf_root_dir . DIRECTORY_SEPARATOR . 'cache' . DIRECTORY_SEPARATOR . 'tmp' . DIRECTORY_SEPARATOR . md5(uniqid(rand(), true));
    sfConfig::set('sf_module_cache_dir', $tmp_dir);
    $generator_manager = new sfGeneratorManager();
    $generator_manager->initialize();
    $generator_manager->generate('sfPropelCrudGenerator', array('model_class' => $model_class, 'moduleName' => $module, 'theme' => $theme));
    $moduleDir = $sf_root_dir . '/' . sfConfig::get('sf_apps_dir_name') . '/' . $app . '/' . sfConfig::get('sf_app_module_dir_name') . '/' . $module;
    // copy our generated module
    $finder = pakeFinder::type('any');
    pake_mirror($finder, $tmp_dir . '/auto' . ucfirst($module), $moduleDir);
    // change module name
    pake_replace_tokens($moduleDir . '/actions/actions.class.php', getcwd(), '', '', array('auto' . ucfirst($module) => $module));
    try {
        $author_name = $task->get_property('author', 'symfony');
    } catch (pakeException $e) {
        $author_name = 'Your name here';
    }
    $constants = array('PROJECT_NAME' => $task->get_property('name', 'symfony'), 'APP_NAME' => $app, 'MODULE_NAME' => $module, 'MODEL_CLASS' => $model_class, 'AUTHOR_NAME' => $author_name);
    // customize php and yml files
    $finder = pakeFinder::type('file')->name('*.php', '*.yml');
    pake_replace_tokens($finder, $moduleDir, '##', '##', $constants);
    // create basic test
    pake_copy(sfConfig::get('sf_symfony_data_dir') . '/skeleton/module/test/actionsTest.php', $sf_root_dir . '/test/functional/' . $app . '/' . $module . 'ActionsTest.php');
    // customize test file
    pake_replace_tokens($module . 'ActionsTest.php', $sf_root_dir . '/test/functional/' . $app, '##', '##', $constants);
    // delete temp files
    $finder = pakeFinder::type('any');
    pake_remove($finder, $tmp_dir);
}
Пример #3
0
 /**
  * Creates a sample yaml configuration file used to drive the build for a given extension.
  * Will ask to overwrite an existing config file if found, unless option overwrite-existing is given
  */
 static function run_generate_extension_config($task = null, $args = array(), $cliopts = array())
 {
     self::setConfigDir($cliopts);
     $overwrite = @$cliopts['overwrite-existing'];
     if (count($args) == 0) {
         throw new pakeException("Missing extension name");
     }
     $extname = $args[0];
     $configfile = self::getOptionsDir() . "/options-{$extname}.yaml";
     if (file_exists($configfile) && !$overwrite) {
         pake_echo("File {$configfile} already exists. Must overwrite it to continue");
         $ok = pake_input("Do you want to overwrite it? [y/n]", 'n');
         if ($ok != 'y') {
             return;
         }
     }
     pake_mkdirs(self::getOptionsDir());
     pake_copy(self::getResourceDir() . '/options-sample.yaml', $configfile, array('override' => true));
     pake_echo("Created file {$configfile}, now go and edit it");
 }
Пример #4
0
 /**
  * Creates the MS WPI
  */
 public static function run_dist_wpi($task = null, $args = array(), $cliopts = array())
 {
     $opts = self::getOpts($args, $cliopts);
     if ($opts['create']['mswpipackage']) {
         pake_mkdirs($opts['dist']['dir']);
         $toppath = $opts['build']['dir'] . '/release';
         $rootpath = $toppath . '/' . self::getProjName();
         if ($opts['create']['mswpipackage']) {
             // add extra files to build
             /// @todo move this to another phase/task... ?
             /// @todo shall we check that there's no spurious file in $toppath?
             $resourcesPath = self::getResourceDir();
             pake_copy($resourcesPath . '/wpifiles/install.sql', $toppath . '/install.sql', array('override' => true));
             /// @todo: if the $rootpath is different from "ezpublish", the manifest and parameters files need to be altered accordingly
             /// after copying them to their location
             pake_copy($resourcesPath . '/wpifiles/manifest.xml', $toppath . '/manifest.xml', array('override' => true));
             pake_copy($resourcesPath . '/wpifiles/parameters.xml', $toppath . '/parameters.xml', array('override' => true));
             // this one is overwritten
             pake_copy($resourcesPath . '/wpifiles/kickstart.ini', $rootpath . '/kickstart.ini', array('override' => true));
             if (is_file($rootpath . '/web.config-RECOMMENDED')) {
                 pake_copy($rootpath . '/web.config-RECOMMENDED', $rootpath . '/web.config', array('override' => true));
             } else {
                 if (!is_file($rootpath . '/web.config')) {
                     pake_copy($resourcesPath . '/wpifiles/web.config', $rootpath . '/web.config', array('override' => true));
                 }
             }
             // create zip
             /// @todo if name is empty do not add an extra hyphen
             $filename = self::getProjFileName() . '-wpi.zip';
             $target = $opts['dist']['dir'] . '/' . $filename;
             self::archiveDir($toppath, $target, true);
             // update feed file
             $feedfile = 'ezpcpmswpifeed.xml';
             pake_copy($resourcesPath . '/wpifiles/' . $feedfile, $opts['dist']['dir'] . '/' . $feedfile);
             $files = pakeFinder::type('file')->name($feedfile)->maxdepth(0)->in($opts['dist']['dir']);
             //pake_replace_regexp( $files, $opts['dist']['dir'], array(
             //) );
             pake_replace_tokens($files, $opts['dist']['dir'], '{', '}', array('$update_date' => gmdate('c'), '$version' => $opts['version']['alias'], '$sha1' => sha1_file($target), '$filename' => $filename, '$filesizeKB' => round(filesize($target) / 1024)));
         }
     }
 }
Пример #5
0
function pake_mirror($arg, $origin_dir, $target_dir, $options = array())
{
    $files = pakeApp::get_files_from_argument($arg, $origin_dir, true);
    foreach ($files as $file) {
        if (is_dir($origin_dir . DIRECTORY_SEPARATOR . $file)) {
            pake_mkdirs($target_dir . DIRECTORY_SEPARATOR . $file);
        } else {
            if (is_file($origin_dir . DIRECTORY_SEPARATOR . $file)) {
                pake_copy($origin_dir . DIRECTORY_SEPARATOR . $file, $target_dir . DIRECTORY_SEPARATOR . $file, $options);
            } else {
                if (is_link($origin_dir . DIRECTORY_SEPARATOR . $file)) {
                    pake_symlink($origin_dir . DIRECTORY_SEPARATOR . $file, $target_dir . DIRECTORY_SEPARATOR . $file);
                } else {
                    throw new pakeException(sprintf('Unable to determine "%s" type', $file));
                }
            }
        }
    }
}
Пример #6
0
// unit tests
$h->register_glob($h->base_dir . '/unit/*/*Test.php');
// functional tests
$h->register_glob($h->base_dir . '/functional/*Test.php');
$h->register_glob($h->base_dir . '/functional/*/*Test.php');
$ret = $h->run();
if (!$ret) {
    throw new Exception('Some tests failed. Release process aborted!');
}
if (is_file('package.xml')) {
    pake_remove('package.xml', getcwd());
}
pake_copy(getcwd() . '/package.xml.tmpl', getcwd() . '/package.xml');
// add class files
$finder = pakeFinder::type('file')->ignore_version_control()->relative();
$xml_classes = '';
$dirs = array('lib' => 'php', 'data' => 'data');
foreach ($dirs as $dir => $role) {
    $class_files = $finder->in($dir);
    foreach ($class_files as $file) {
        $xml_classes .= '<file role="' . $role . '" baseinstalldir="symfony" install-as="' . $file . '" name="' . $dir . '/' . $file . '" />' . "\n";
    }
}
// replace tokens
pake_replace_tokens('package.xml', getcwd(), '##', '##', array('SYMFONY_VERSION' => $version, 'CURRENT_DATE' => date('Y-m-d'), 'CLASS_FILES' => $xml_classes, 'STABILITY' => $stability));
$results = pake_sh('pear package');
echo $results;
pake_remove('package.xml', getcwd());
// copy .tgz as symfony-latest.tgz
pake_copy(getcwd() . '/symfony-' . $version . '.tgz', getcwd() . '/symfony-latest.tgz');
exit(0);
Пример #7
0
function run_create_package_xml()
{
    $_root = dirname(__FILE__);
    $options = pakeYaml::loadFile($_root . '/options.yaml');
    $version = $options['version'];
    // create a pear package
    pake_echo_comment('creating PEAR package.xml for version "' . $version . '"');
    pake_copy($_root . '/package.xml.tmpl', $_root . '/package.xml', array('override' => true));
    // add class files
    $class_files = pakeFinder::type('file')->ignore_version_control()->not_name('/^pakeApp.class.php$/')->name('*.php')->maxdepth(0)->relative()->in($_root . '/lib/pake');
    $task_files = pakeFinder::type('file')->ignore_version_control()->name('*.php')->relative()->in($_root . '/lib/pake/tasks');
    $renames = '';
    $xml_classes = '';
    $task_classes = '';
    foreach ($class_files as $file) {
        $xml_classes .= '<file role="php" name="' . $file . '"/>' . "\n";
        $renames .= '<install as="pake/' . $file . '" name="lib/pake/' . $file . '"/>' . "\n";
    }
    foreach ($task_files as $file) {
        $task_classes .= '<file role="php" name="' . $file . '"/>' . "\n";
        $renames .= '<install as="pake/tasks/' . $file . '" name="lib/pake/tasks/' . $file . '"/>' . "\n";
    }
    // replace tokens
    pake_replace_tokens('package.xml', $_root, '##', '##', array('PAKE_VERSION' => $version, 'CURRENT_DATE' => date('Y-m-d'), 'CLASS_FILES' => $xml_classes, 'TASK_FILES' => $task_classes, 'RENAMES' => $renames));
}
Пример #8
0
 /**
  * Generates a sample package.xml to allow creation of packaged extension
  *
  * NB: that file is to be completed by hand
  */
 static function run_generate_sample_package_xml($task = null, $args = array(), $cliopts = array())
 {
     pake_copy(self::getResourceDir() . '/package_master.xml', 'package.xml');
     // tokens not replaced here are replaced at build time
     // tokens in square brackets are supposed to be edited by the developer
     $tokens = array('$summary' => '[Summary]', '$description' => '[Description]', '$vendor' => '', '$maintainers' => '', '$documents' => '', '$changelog' => '', '$simple-files' => '', '$state' => '[State]', '$requires' => '');
     //$files = pakeFinder::type( 'file' )->name( 'package.xml' )->maxdepth( 0 )->in( '.' );
     pake_replace_tokens('package.xml', '.', '{', '}', $tokens);
     pake_echo("File package.xml generated. Please replace all tokens in square brackets in it (but do not replace values in curly brackets) then commit it to sources in the top dir of the extension");
 }
Пример #9
0
function _propel_copy_xml_schema_from_plugins($prefix = '')
{
    $schemas = pakeFinder::type('file')->name('*schema.xml')->in(glob(sfConfig::get('sf_root_dir') . '/plugins/*/config'));
    foreach ($schemas as $schema) {
        // reset local prefix
        $localprefix = '';
        // change prefix for plugins
        if (preg_match('#plugins[/\\\\]([^/\\\\]+)[/\\\\]#', $schema, $match)) {
            // if the plugin name is not in the schema filename, add it
            if (!strstr(basename($schema), $match[1])) {
                $localprefix = $match[1] . '-';
            }
        }
        // if the prefix is not in the schema filename, add it
        if (!strstr(basename($schema), $prefix)) {
            $localprefix = $prefix . $localprefix;
        }
        pake_copy($schema, 'config' . DIRECTORY_SEPARATOR . $localprefix . basename($schema));
        if ('' === $localprefix) {
            pake_remove($schema, '');
        }
    }
}
Пример #10
0
function run_init_controller($task, $args)
{
    // handling two required arguments (application and batch name)
    if (count($args) < 2) {
        throw new Exception('You must provide the environment name');
    }
    $app = $args[0];
    $env = $args[1];
    // handling two optional arguments (environment and debug)
    $controller = isset($args[2]) ? $args[2] : $app . '_' . $env;
    $debug = isset($args[3]) ? $args[3] : true;
    $constants = array('PROJECT_NAME' => $task->get_property('name', 'symfony'), 'APP_NAME' => $app, 'CONTROLLER_NAME' => $controller, 'ENV_NAME' => $env, 'DEBUG' => (bool) $debug);
    $sf_web_dir = sfConfig::get('sf_web_dir');
    pake_copy(sfConfig::get('sf_symfony_data_dir') . '/skeleton/controller/controller.php', $sf_web_dir . '/' . $controller . '.php');
    pake_replace_tokens($controller . '.php', $sf_web_dir, '##', '##', $constants);
}
Пример #11
0
function _add_1_0_test_bootstraps()
{
    pake_echo_action('upgrade 1.0', 'add test bootstrap files');
    pake_mkdirs(sfConfig::get('sf_root_dir') . '/test/bootstrap');
    pake_copy(sfConfig::get('sf_symfony_data_dir') . '/skeleton/project/test/bootstrap/functional.php', sfConfig::get('sf_root_dir') . '/test/bootstrap/functional.php');
    pake_copy(sfConfig::get('sf_symfony_data_dir') . '/skeleton/project/test/bootstrap/unit.php', sfConfig::get('sf_root_dir') . '/test/bootstrap/unit.php');
}
Пример #12
0
 /**
  * @todo allow via CLI to specify dir for tarballs
  * @todo simplify management of title for docs: just get it whole from configs...
  * @todo split this monster in smaller pieces
  */
 public static function run_generate_apidocs_generic($stack, $task = null, $args = array(), $cliopts = array())
 {
     $opts = self::getOpts($args, $cliopts);
     $sourcedir = @$cliopts['sourcedir'];
     $docsdir = @$cliopts['docsdir'];
     switch ($stack) {
         case 'LS':
             $excludedirs = $opts['docs']['exclude_dirs']['legacy_stack'];
             if ($sourcedir == '') {
                 $sourcedir = $opts['build']['dir'] . '/release/' . self::getProjName() . '/ezpublish_legacy';
             } else {
                 $sourcedir .= '/ezpublish_legacy';
             }
             if ($docsdir == '') {
                 $docsdir = $opts['build']['dir'] . '/apidocs/' . self::getProjName() . '/ezpublish_legacy';
             }
             $files = pakeFinder::type('file')->name('autoload.php')->maxdepth(0)->in($sourcedir);
             $namesuffix = $opts['docs']['name_suffix']['legacy_stack'];
             break;
         case '4X':
             $excludedirs = $opts['docs']['exclude_dirs']['legacy_stack'];
             if ($sourcedir == '') {
                 $sourcedir = $opts['build']['dir'] . '/release/' . self::getProjName();
             }
             if ($docsdir == '') {
                 $docsdir = $opts['build']['dir'] . '/apidocs/' . self::getProjName();
             }
             $files = pakeFinder::type('file')->name('runcronjobs.php')->maxdepth(0)->in($sourcedir);
             $namesuffix = $opts['docs']['name_suffix']['4x_stack'];
             break;
         default:
             $stack = 'NS';
             $excludedirs = $opts['docs']['exclude_dirs']['new_stack'];
             if ($sourcedir == '') {
                 $sourcedir = $opts['build']['dir'] . '/release/' . self::getProjName();
             }
             if ($docsdir == '') {
                 $docsdir = $opts['build']['dir'] . '/apidocs/' . self::getProjName() . '/ezpublish';
             }
             $files = pakeFinder::type('file')->name('autoload.php')->maxdepth(0)->in($sourcedir . '/ezpublish');
             // allow building from sources, not only from release
             if (!count($files)) {
                 $files = pakeFinder::type('directory')->name('eZ')->maxdepth(0)->in($sourcedir);
             }
             $namesuffix = $opts['docs']['name_suffix']['new_stack'];
     }
     if ($opts['create']['doxygen_doc'] || $opts['create']['docblox_doc'] || $opts['create']['phpdoc_doc'] || $opts['create']['sami_doc']) {
         if (!count($files)) {
             throw new pakeException("Can not generate documentation: no sources found in {$sourcedir}");
         }
     }
     $excludedirs = explode(' ', $excludedirs);
     if ($namesuffix != '') {
         $namesuffix = ' ' . $namesuffix;
     }
     if ($opts['create']['doxygen_doc']) {
         pake_echo("Generating docs using Doxygen");
         $doxygen = self::getTool('doxygen', $opts);
         if ($opts['docs']['doxygen']['dir'] != '') {
             $outdir = $opts['docs']['doxygen']['dir'];
         } else {
             $outdir = $docsdir . '/doxygen';
         }
         if ($opts['docs']['doxygen']['zipdir'] != '') {
             $zipdir = $opts['docs']['doxygen']['zipdir'];
         } else {
             $zipdir = $opts['dist']['dir'];
         }
         $doxyfile = $opts['build']['dir'] . '/doxyfile';
         $excludes = '';
         foreach ($excludedirs as $excluded) {
             $excludes .= "{$sourcedir}/{$excluded} ";
         }
         pake_copy($opts['docs']['doxyfile_master'], $doxyfile, array('override' => true));
         file_put_contents($doxyfile, "\nPROJECT_NAME = " . self::getLongProjName(true, $namesuffix) . "\nPROJECT_NUMBER = " . $opts['version']['alias'] . "\nOUTPUT_DIRECTORY = " . $outdir . "\nINPUT = " . $sourcedir . "\nEXCLUDE = " . $excludes . "\nSTRIP_FROM_PATH = " . $sourcedir . "\nSOURCE_BROWSER = " . ($opts['docs']['include_sources'] ? 'yes' : 'no'), FILE_APPEND);
         pake_mkdirs($outdir);
         pake_remove_dir($outdir . '/html');
         $out = pake_sh("{$doxygen} " . escapeshellarg($doxyfile) . ' > ' . escapeshellarg($outdir . '/generate.log'));
         // test that there are any doc files created
         $files = pakeFinder::type('file')->name('index.html')->maxdepth(0)->in($outdir . '/html');
         if (!count($files)) {
             throw new pakeException("Doxygen did not generate index.html file in {$outdir}/html");
         }
         // zip the docs
         pake_echo("Creating tarballs of docs");
         $filename = self::getProjFileName() . '-apidocs-doxygen-' . $stack;
         // get absolute path to dist dir
         $target = realpath($zipdir) . '/' . $filename;
         if ($opts['docs']['create']['zip']) {
             self::archiveDir($outdir . '/html', $target . '.zip', true);
         }
         if ($opts['docs']['create']['tgz']) {
             self::archiveDir($outdir . '/html', $target . '.tar.gz', true);
         }
         if ($opts['docs']['create']['bz2']) {
             self::archiveDir($outdir . '/html', $target . '.tar.bz2', true);
         }
     }
     if ($opts['create']['sami_doc']) {
         pake_echo("Generating docs using Sami");
         $sami = self::getTool('sami', $opts, true);
         if ($opts['docs']['sami']['dir'] != '') {
             $outdir = $opts['docs']['sami']['dir'];
         } else {
             $outdir = $docsdir . '/sami';
         }
         if ($opts['docs']['sami']['zipdir'] != '') {
             $zipdir = $opts['docs']['sami']['zipdir'];
         } else {
             $zipdir = $opts['dist']['dir'];
         }
         $samifile = $opts['build']['dir'] . '/samicfg.php';
         $excludes = array();
         foreach ($excludedirs as $excluded) {
             $excludes[] = str_replace("'", "\\'", $excluded);
         }
         $excludes = implode("' )\n    ->exclude( '", $excludes);
         pake_copy(self::getResourceDir() . '/samicfg_master.php', $samifile, array('override' => true));
         pake_replace_tokens('samicfg.php', $opts['build']['dir'], '//', '//', array('SOURCE' => str_replace("'", "\\'", $sourcedir), 'TITLE' => self::getLongProjName(true, $namesuffix) . ' ' . $opts['version']['alias'], 'EXCLUDE' => $excludes, 'OUTPUT' => $outdir . '/html', 'CACHEDIR' => $opts['build']['dir'] . '/sami_cache', 'BASEDIR' => dirname(__DIR__)));
         //clear sami cache, as sometimes it prevents docs from generating correctly
         pake_remove_dir($opts['build']['dir'] . '/sami_cache');
         pake_mkdirs($outdir);
         pake_remove_dir($outdir . '/html');
         $php = self::getTool('php', $opts);
         $out = pake_sh("{$php} {$sami} parse --force " . escapeshellarg($samifile) . ' > ' . escapeshellarg($outdir . '/generate.log'));
         $out = pake_sh("{$php} {$sami} render " . escapeshellarg($samifile) . ' >> ' . escapeshellarg($outdir . '/generate.log'));
         // test that there are any doc files created
         $files = pakeFinder::type('file')->name('index.html')->maxdepth(0)->in($outdir . '/html');
         if (!count($files)) {
             throw new pakeException("Sami did not generate index.html file in {$outdir}/html");
         }
         // zip the docs
         pake_echo("Creating tarballs of docs");
         $filename = self::getProjFileName() . '-apidocs-sami-' . $stack;
         // get absolute path to dist dir
         $target = realpath($zipdir) . '/' . $filename;
         if ($opts['docs']['create']['zip']) {
             self::archiveDir($outdir . '/html', $target . '.zip', true);
         }
         if ($opts['docs']['create']['tgz']) {
             self::archiveDir($outdir . '/html', $target . '.tar.gz', true);
         }
         if ($opts['docs']['create']['bz2']) {
             self::archiveDir($outdir . '/html', $target . '.tar.bz2', true);
         }
     }
     if ($opts['create']['docblox_doc']) {
         pake_echo("Generating docs using Docblox");
         $docblox = self::getTool('docblox', $opts);
         if ($opts['docs']['docblox']['dir'] != '') {
             $outdir = $opts['docs']['docblox']['dir'];
         } else {
             $outdir = $docsdir . '/docblox';
         }
         if ($opts['docs']['docblox']['zipdir'] != '') {
             $zipdir = $opts['docs']['docblox']['zipdir'];
         } else {
             $zipdir = $opts['dist']['dir'];
         }
         pake_mkdirs($outdir);
         pake_remove_dir($outdir . '/html');
         $php = self::getTool('php', $opts);
         $out = pake_sh("{$php} -d memory_limit=3000M {$docblox}" . ' -d ' . escapeshellarg($sourcedir) . ' -t ' . escapeshellarg($outdir . '/html') . ' --title ' . escapeshellarg(self::getLongProjName(true, $namesuffix) . ' ' . $opts['version']['alias']) . ' --ignore ' . escapeshellarg(implode(',', $excludedirs)) . ($opts['docs']['include_sources'] ? ' --sourcecode' : '') . ' > ' . escapeshellarg($outdir . '/docblox/generate.log'));
         /// @todo sed -e "s,${checkoutpath},,g" ${doxydir}/generate.log > ${doxydir}/generate2.log
         // test that there are any doc files created
         $files = pakeFinder::type('file')->name('index.html')->maxdepth(0)->in($outdir . '/html');
         if (!count($files)) {
             throw new pakeException("Docblox did not generate index.html file in {$outdir}/html");
         }
         // zip the docs
         pake_echo("Creating tarballs of docs");
         $filename = self::getProjFileName() . '-apidocs-docblox-' . $stack;
         $target = realpath($zipdir) . '/' . $filename;
         if ($opts['docs']['create']['zip']) {
             self::archiveDir($outdir . '/html', $target . '.zip', true);
         }
         if ($opts['docs']['create']['tgz']) {
             self::archiveDir($outdir . '/html', $target . '.tar.gz', true);
         }
         if ($opts['docs']['create']['bz2']) {
             self::archiveDir($outdir . '/html', $target . '.tar.bz2', true);
         }
     }
     if ($opts['create']['phpdoc_doc']) {
         pake_echo("Generating docs using PhpDoc");
         $phpdoc = self::getTool('phpdoc', $opts, true);
         if ($opts['docs']['phpdoc']['dir'] != '') {
             $outdir = $opts['docs']['phpdoc']['dir'];
         } else {
             $outdir = $docsdir . '/phpdoc';
         }
         if ($opts['docs']['phpdoc']['zipdir'] != '') {
             $zipdir = $opts['docs']['phpdoc']['zipdir'];
         } else {
             $zipdir = $opts['dist']['dir'];
         }
         pake_mkdirs($outdir . '/html');
         // we try to avoid deprecation errors from phpdoc
         $errcode = 30719;
         // php 5.3, 5.4
         if (version_compare(PHP_VERSION, '5.3.0') < 0) {
             $errcode = 6143;
         }
         // phpdoc uses A LOT of memory as well
         $php = self::getTool('php', $opts);
         $out = pake_sh("{$php} -d error_reporting={$errcode} -d memory_limit=3000M {$phpdoc}" . ' -t ' . escapeshellarg($outdir . '/html') . ' -d ' . escapeshellarg($sourcedir) . ' --parseprivate' . ' --title ' . escapeshellarg(self::getLongProjName(true, $namesuffix) . ' ' . $opts['version']['alias']) . ' -i ' . escapeshellarg(implode('/*,', $excludedirs) . '/*') . ($opts['docs']['include_sources'] ? ' --sourcecode' : '') . ' > ' . escapeshellarg($outdir . '/generate.log'));
         /// @todo sed -e "s,${phpdocdir},,g" ${phpdocdir}/generate.log > ${phpdocdir}/generate2.log
         ///       sed -e "s,${checkoutpath},,g" ${phpdocdir}/generate2.log > ${phpdocdir}/generate3.log
         ///       sed -e "s,${phpdocinstall},,g" ${phpdocdir}/generate3.log > ${phpdocdir}/generate4.log
         // test that there are any doc files created
         $files = pakeFinder::type('file')->name('index.html')->maxdepth(0)->in($outdir . '/html');
         if (!count($files)) {
             throw new pakeException("Phpdoc did not generate index.html file in {$outdir}/phpdoc/html");
         }
         // clear phpdoc cache, as it is generated in same folder as doc artifacts and there is apparently no option
         // to have it somewhere else
         foreach (PakeFinder::type('dir')->maxdepth(1)->name('phpdoc-cache-*')->in($outdir . '/html') as $dir) {
             pake_remove_dir($dir);
         }
         // zip the docs
         pake_echo("Creating tarballs of docs");
         $filename = self::getProjFileName() . '-apidocs-phpdoc-' . $stack;
         $target = realpath($zipdir) . '/' . $filename;
         if ($opts['docs']['create']['zip']) {
             self::archiveDir($outdir . '/html', $target . '.zip', true);
         }
         if ($opts['docs']['create']['tgz']) {
             self::archiveDir($outdir . '/html', $target . '.tar.gz', true);
         }
         if ($opts['docs']['create']['bz2']) {
             self::archiveDir($outdir . '/html', $target . '.tar.bz2', true);
         }
     }
 }