PK C,CV?
composer.locknu W+A {
"_readme": [
"This file locks the dependencies of your project to a known state",
"Read more about it at http://getcomposer.org/doc/01-basic-usage.md#composer-lock-the-lock-file"
],
"hash": "17dc3dcd23cd9cf5e79a956a4fe7b6b8",
"packages": [
{
"name": "symfony/console",
"version": "v2.4.1",
"target-dir": "Symfony/Component/Console",
"source": {
"type": "git",
"url": "https://github.com/symfony/Console.git",
"reference": "4c1ed2ff514bd85ee186eebb010ccbdeeab05af7"
},
"dist": {
"type": "zip",
"url": "https://api.github.com/repos/symfony/Console/zipball/4c1ed2ff514bd85ee186eebb010ccbdeeab05af7",
"reference": "4c1ed2ff514bd85ee186eebb010ccbdeeab05af7",
"shasum": ""
},
"require": {
"php": ">=5.3.3"
},
"require-dev": {
"symfony/event-dispatcher": "~2.1"
},
"suggest": {
"symfony/event-dispatcher": ""
},
"type": "library",
"extra": {
"branch-alias": {
"dev-master": "2.4-dev"
}
},
"autoload": {
"psr-0": {
"Symfony\\Component\\Console\\": ""
}
},
"notification-url": "https://packagist.org/downloads/",
"license": [
"MIT"
],
"authors": [
{
"name": "Fabien Potencier",
"email": "fabien@symfony.com"
},
{
"name": "Symfony Community",
"homepage": "http://symfony.com/contributors"
}
],
"description": "Symfony Console Component",
"homepage": "http://symfony.com",
"time": "2014-01-01 08:14:50"
}
],
"packages-dev": [
],
"aliases": [
],
"minimum-stability": "alpha",
"stability-flags": [
],
"platform": [
],
"platform-dev": [
]
}
PK C,CVxC C LICENSEnu W+A The MIT License (MIT)
Copyright (c) 2014 Codegyre developers team
Permission is hereby granted, free of charge, to any person obtaining a copy of
this software and associated documentation files (the "Software"), to deal in
the Software without restriction, including without limitation the rights to
use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of
the Software, and to permit persons to whom the Software is furnished to do so,
subject to the following conditions:
The above copyright notice and this permission notice shall be included in all
copies or substantial portions of the Software.
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS
FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR
COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
PK C,CV]Px x robonu W+A #!/usr/bin/env php
execute();PK C,CVX6 RoboFile.phpnu W+A say("Releasing Robo");
$this->taskExec("git tag")->args(\Robo\Runner::VERSION)->run();
$this->taskExec("git push origin master --tags")->run();
}
}PK C,CVd
composer.jsonnu W+A {
"name": "codegyre/robo",
"description": "Modern task runner",
"minimum-stability": "alpha",
"license": "MIT",
"authors": [
{
"name": "Davert",
"email": "davert.php@resend.cc"
}
],
"autoload":{
"psr-4":{
"Robo\\":"src"
}
},
"bin":["robo"],
"require": {
"symfony/console": "*"
}
}PK C,CVV
.gitignorenu W+A vendor/
.idea/PK C,CV@ README.mdnu W+A RoboTask
====
Modern and simple task runner for PHP. Is aimed to automate common tasks:
* executing daemons (and workers)
* performing cleanups
* building release
* running multiple Symfony Commands
* starting PHP server
* running tests
* writing cross-platform scripts
## Installing
### Composer
* Add `"codegyre/robo": "*"` to `composer.json`.
* Run `composer install`
* Use `vendor/bin/robo` to execute robo tasks.
## Usage
All tasks are defined as **public methods** in `RoboFile.php`. It can be created by running `robo init`.
RoboFile has a set of predefined tasks taken from `\Robo\Tasks`. All tasks are included with traits.
All protected methods in traits that start with `task` prefix are predefined tasks and can be configured and executed in your tasks.
There are predefined tasks that can be executed from RoboFile
* `taskExec` executes script. Optionally can be started in background.
* `taskServer` starts PHP server. Optionally can be stopped on exit
* `taskCopyDir` copies one dir into another
* `taskCleanDir` empties specified dir
* `taskDeleteDir` removes dir
* `taskCommand` running Symfony Command. *(requires \Robo\Add\Command trait)*
* `taskPackPhar` creating phar archive *(requires \Robo\Add\Command trait)*
## Example: running Codeception Acceptance Test
To run test we need to start a server first, and launch a Selenium Server
``` php
taskServer(8000)
->background()
->dir('web')
->run();
// running Selenium server in background
$this->taskExec('java -jar '.$pathToSelenium)
->background()
->run();
// loading Symfony Command and running with passed argument
$this->taskCommand(new \Codeception\Command\Run('run'))
->arg('suite','acceptance')
->run();
}
}
?>
```
If you execute `robo` you will see this task added to list of available task with name: `test:acceptance`.
To execute it you shoud run `robo test:acceptance`. You may change path to selenium server by passing new path as a argument:
```
robo test:acceptance "C:\Downloads\selenium.jar"
```
## Example: Cleaning Logs and Cache
``` php
taskCleanDir([
'app/cache'
'app/logs'
])->run();
$this->taskDeleteDir([
'web/assets/tmp_uploads',
])->run();
}
?>
```
This task cleans `app/cache` and `app/logs` dirs (ignoreing .gitignore and .gitkeep files)
Can be executed by running:
```
robo clean
```
## Example: Creating Phar Archive
This example was extracted from Codeception and simplified:
``` php
function buildPhar()
{
$pharTask = $this->taskPackPhar('package/codecept.phar')
->compress()
->stub('package/stub.php');
$finder = Finder::create()
->ignoreVCS(true)
->name('*.php')
->in('src');
foreach ($finder as $file) {
$pharTask->addFile('src/'.$file->getRelativePathname(), $file->getRealPath());
}
$finder = Finder::create()->files()
->ignoreVCS(true)
->name('*.php')
->exclude('Tests')
->exclude('tests')
->in('vendor');
foreach ($finder as $file) {
$pharTask->addStripped('vendor/'.$file->getRelativePathname(), $file->getRealPath());
}
$pharTask->addFile('autoload.php', 'autoload.php')
->addFile('codecept', 'package/bin')
->run();
$code = $this->taskExec('php package/codecept.phar')->run();
if ($code !== 0) {
throw new Exception("There was problem compiling phar");
}
}
```
[This and other example tasks](https://github.com/Codeception/Codeception/blob/2.0-dev/RoboFile.php). can be found in Codeception repoPK C,CVЊI
src/Tasks.phpnu W+A dirs as $src => $dst) {
FileSystem::copyDir($src, $dst);
$this->printTaskInfo("Copied from $src to $dst");
}
}
}
PK C,CVB src/Task/PackPhar.phpnu W+A filename = $filename;
@unlink($file->getRealPath());
$this->phar = new \Phar($file->getPathname(), 0, $file->getFilename());
}
/**
* @param boolean $compress
* @return $this
*/
public function compress($compress = true)
{
$this->compress = $compress;
return $this;
}
public function stub($stub)
{
$this->phar->setStub(file_get_contents($stub));
return $this;
}
public function run()
{
$this->printTaskInfo("creating {$this->filename}");
$this->phar->setSignatureAlgorithm(\Phar::SHA1);
$this->phar->startBuffering();
$this->printTaskInfo('packing '.count($this->files).' files into phar');
$progress = new ProgressHelper();
$progress->start($this->output(), count($this->files));
foreach ($this->files as $path => $content) {
$this->phar->addFromString($path, $content);
$progress->advance();
}
$this->phar->stopBuffering();
$progress->finish();
if($this->compress and in_array('GZ', \Phar::getSupportedCompression())) {
$this->taskInfo($this->filename . " compressed");
$this->phar = $this->phar->compressFiles(\Phar::GZ);
}
$this->printTaskInfo($this->filename." produced");
}
public function addStripped($path, $file)
{
$this->files[$path] = $this->stripWhitespace(file_get_contents($file));
return $this;
}
public function addFile($path, $file)
{
$this->files[$path] = file_get_contents($file);
return $this;
}
/**
* Strips whitespace from source. Taken from composer
* @param $source
* @return string
*/
private function stripWhitespace($source)
{
if (!function_exists('token_get_all')) {
return $source;
}
$output = '';
foreach (token_get_all($source) as $token) {
if (is_string($token)) {
$output .= $token;
} elseif (in_array($token[0], array(T_COMMENT, T_DOC_COMMENT))) {
// $output .= $token[1];
$output .= str_repeat("\n", substr_count($token[1], "\n"));
} elseif (T_WHITESPACE === $token[0]) {
// reduce wide spaces
$whitespace = preg_replace('{[ \t]+}', ' ', $token[1]);
// normalize newlines to \n
$whitespace = preg_replace('{(?:\r\n|\r|\n)}', "\n", $whitespace);
// trim leading spaces
$whitespace = preg_replace('{\n +}', "\n", $whitespace);
$output .= $whitespace;
} else {
$output .= $token[1];
}
}
return $output;
}
}
PK C,CVA`< < src/Task/Exec.phpnu W+A command = $command;
}
public function background()
{
$this->isBackground = true;
return $this;
}
public function args($arg)
{
if (!is_array($arg)) {
$arg = func_get_args();
}
$this->command .= " ".implode(' ', $arg);
return $this;
}
public function __destruct()
{
$this->stop();
}
public function stop()
{
if ($this->isBackground && $this->resource !== null) {
foreach ($this->pipes AS $pipe) {
fclose($pipe);
}
proc_terminate($this->resource, 2);
unset($this->resource);
$this->printTaskInfo("stopped {$this->command}");
}
}
public function run()
{
$this->printTaskInfo("running {$this->command}");
if (!$this->isBackground and $this->isPrinted) {
system($this->command, $code);
return $code;
}
if (!$this->isBackground and !$this->isPrinted) {
exec($this->command, $output, $code);
return $code;
}
$descriptor = [
['pipe', 'r'],
['pipe', 'r'],
['pipe', 'r']
];
$this->resource = proc_open($this->command, $descriptor, $this->pipes, null, null, ['bypass_shell' => true]);
if (!is_resource($this->resource)) {
throw new TaskException($this, 'Failed to run command.');
}
if (!proc_get_status($this->resource)['running']) {
proc_close($this->resource);
throw new TaskException($this, 'Failed to run command.');
}
}
}
PK C,CV. . src/Task/DeleteDir.phpnu W+A dirs as $dir) {
FileSystem::deleteDir($dir);
$this->printTaskInfo("deleted $dir...");
}
}
}
PK C,CV\^@= = src/Task/BaseDir.phpnu W+A dirs = $dirs
: $this->dirs[] = $dirs;
}
}
PK C,CVJa-j src/Task/CleanDir.phpnu W+A dirs as $dir) {
FileSystem::doEmptyDir($dir);
$this->printTaskInfo("cleaned $dir");
}
}
}
PK C,CVbm? src/Runner.phpnu W+A output = new ConsoleOutput();
}
protected function loadRoboFile()
{
if (!file_exists(self::ROBOFILE)) {
$this->output->writeln(" ".self::ROBOFILE." not found in this dir ");
$dialog = new DialogHelper();
if ($dialog->askConfirmation($this->output, " Should I create RoboFile here? (y/n) \n", false)) {
$this->initRoboFile();
}
exit;
}
require_once self::ROBOFILE;
if (!class_exists(self::ROBOCLASS)) {
$this->output->writeln("Class ".self::ROBOCLASS." was not loaded");
return false;
}
return true;
}
public function execute()
{
$app = new Application('Robo', self::VERSION);
$loaded = $this->loadRoboFile();
if (!$loaded) {
$app->add(new Init('init'));
$app->run();
return;
}
$className = self::ROBOCLASS;
$roboTasks = new $className;
$taskNames = get_class_methods(self::ROBOCLASS);
foreach ($taskNames as $taskName) {
$command = $this->createCommand($taskName);
$command->setCode(function(InputInterface $input) use ($roboTasks, $taskName) {
$args = $input->getArguments();
array_shift($args);
$args[] = $input->getOptions();
call_user_func_array([$roboTasks, $taskName], $args);
});
$app->add($command);
}
$app->run();
}
protected function createCommand($taskName)
{
$taskInfo = new TaskInfo(self::ROBOCLASS, $taskName);
$task = new Command($taskInfo->getName());
$task->setDescription($taskInfo->getDescription());
$args = $taskInfo->getArguments();
foreach ($args as $name => $val) {
if ($val === TaskInfo::PARAM_IS_REQUIRED) {
$task->addArgument($name, InputArgument::REQUIRED);
} else {
$task->addArgument($name, InputArgument::OPTIONAL, '', $val);
}
}
return $task;
}
protected function initRoboFile()
{
file_put_contents(self::ROBOFILE, "output->writeln(self::ROBOFILE . " created");
}
}
PK C,CVbVy y src/Util/FileSystem.phpnu W+A isDir()) {
$dir = (string) $path;
if (basename($dir) === '.' || basename($dir) === '..') {
continue;
}
rmdir($dir);
} else {
$file = (string)$path;
if (basename($file) === '.gitignore') {
continue;
}
if (basename($file) === '.gitkeep') {
continue;
}
unlink($path->__toString());
}
}
}
public static function deleteDir($dir)
{
if (!file_exists($dir)) return true;
if (!is_dir($dir) || is_link($dir)) return unlink($dir);
foreach (scandir($dir) as $item) {
if ($item == '.' || $item == '..') continue;
if (!self::deleteDir($dir . "/" . $item)) {
chmod($dir . "/" . $item, 0777);
if (!self::deleteDir($dir . "/" . $item)) return false;
}
}
return rmdir($dir);
}
public static function copyDir($src, $dst)
{
$dir = opendir($src);
@mkdir($dst);
while(false !== ( $file = readdir($dir)) ) {
if (( $file != '.' ) && ( $file != '..' )) {
if ( is_dir($src . '/' . $file) ) {
self::copyDir($src . '/' . $file,$dst . '/' . $file);
}
else {
copy($src . '/' . $file,$dst . '/' . $file);
}
}
}
closedir($dir);
}
}
PK C,CVv/ src/Add/Exec.phpnu W+A runningCommands[] = $exec;
return $exec;
}
protected function taskServer($port)
{
$server = new Server($port);
$this->runningCommands[] = $server;
return $server;
}
}
PK C,CV&˛B B src/Add/FileSystem.phpnu W+A writeln("➜ $text");
}
protected function printTaskInfo($text)
{
$this->writeln(" [".get_class($this)."] $text");
}
/**
* @return ConsoleOutput
*/
protected function getOutput()
{
static $output;
if (!$output) {
$output = new ConsoleOutput();
}
return $output;
}
private function writeln($text)
{
$this->getOutput()->writeln($text);
}
}
PK C,CVV& src/TaskInfo.phpnu W+A reflection = new \ReflectionMethod($className, $methodName);
}
public function getDescription()
{
$desc = $this->getAnnotation('description');
if (!$desc) {
$desc = $this->getAnnotation('desc');
}
return $desc;
}
public function getName()
{
$name = $this->getAnnotation('name');
if (!$name) {
$name = $this->reflection->getName();
}
$name = $this->convertName($name);
return $name;
}
public function getArguments()
{
$args = [];
$params = $this->reflection->getParameters();
foreach ($params as $param) {
if ($param->isArray()) {
continue;
}
$val = $param->isDefaultValueAvailable() ? $param->getDefaultValue() : self::PARAM_IS_REQUIRED;
$args[$param->getName()] = $val;
}
return $args;
}
protected function getAnnotation($annotation)
{
$docBlock = $this->reflection->getDocComment();
$matched = array();
$res = preg_match(sprintf(self::$annotationRegex, $annotation), $docBlock, $matched);
if (!$res) return null;
return $matched[1];
}
private function convertName($camel,$splitter=":")
{
$camel=preg_replace('/(?!^)[[:upper:]][[:lower:]]/', '$0', preg_replace('/(?!^)[[:upper:]]+/', $splitter.'$0', $camel));
return strtolower($camel);
}
}
PK C,CVG G src/TaskInterface.phpnu W+A