如何使用symfony console进度助手?

时间:2014-02-19 22:13:51

标签: php symfony console progress-bar

以示例Symfony Progress Helper

为例

我不确定如何使用它。我正在使用usleep,因为我希望进度条运行直到任务完成。假设任务是一个执行许多其他事情的方法,当它完成时它返回true。当它返回true时我想使用setCurrent来完成进度条。

$progress = $this->getHelperSet()->get('progress');

$progress->start($this->output, 100);

$i = 0;
while ($i++ < 100) {
    usleep(100000);

    $progress->advance();

}

//do stuff and return true when it's done
if($this->doStuff()) $progress->setCurrent(100);

$progress->finish();

在文档中我不清楚这是如何工作的。如果我将我的方法放在循环中,它将运行100次。但是如果我把它放在循环之外,那么在运行我的方法之前循环将运行100次。另外,如果我把它放在$ progress-&gt; finish()之外我得到一个错误,我必须开始()进度条有意义,但如果我把它放在finish()我得到一个logicException“你不能回归进度条“

感谢您的帮助。示例用法很棒。

更新 也许这是不可能的。

让我解释一下我要做些什么来清理它。

我想要一个进度条在屏幕上运行。它设置为比doStuff()实际运行更长的时间。 doStuff()在我的类中基本上是一个fire()方法,可以执行一些其他的操作,包括下载和复制文件。但doStuff()只运行一次。我需要进度条在doStuff()运行的整个过程中运行但是当doStuff()完成时我希望能够将进度条前进到结束或者只是终止它,无论它在循环中的位置。

我尝试在我的doStuff()方法中放入progress-&gt; advance(),但它仍然需要一个循环,因为它只前进一次。所以这就是为什么我需要将doStuff()与进度条循环分开,但能够从doStuff()中终止它。

2 个答案:

答案 0 :(得分:0)

答案归功于JamesHalsall的评论是进度条不能以这种方式工作。如果我想多次循环执行单个任务或一组任务,那么Symfony的示例就可以工作。

但是在这种情况下只有一个任务,doStuff()方法我需要将回调传递给doStuff(),所以doStuff()可以推进进度条。这里不需要循环。还发现advance方法采用整数作为前进步数的参数。

因此,通过一些基本的数学和回调,这实际上是。进度条设置为100,doStuff()中的4个任务100/4 = 25是推进进度条的步数。

这是一个适合我的例子。当然,4个任务中抛出的异常将阻止所有内容,因此即使特定任务失败,也不必担心进度条会完成。

    protected function update()
    {
        $this->progress = $this->getHelperSet()->get('progress');
        $this->progress->setBarCharacter('<comment>=</comment>');
        $this->progress->setBarWidth(50);
        $this->progress->start($this->output, 100);
        $done = false;


        $result = false;

        $advance = function($steps)
        {
            $this->progress->advance($steps);
        };

        $result = $this->doStuff($advance);

        $this->progress->finish();

        if($result === true)
        {
            $this->displayOutput("I be done foo!");
        }
        else
        {
            $this->displayOutput("Somethin went wrong foo!");
        }

    }


    protected function doStuff($callback)
    {
        //simulate tasks with usleep
        //perfom task 1
        usleep(500000);
        $callback(25);

        //perform task 2
        usleep(500000);
        $callback(25);

        //task 3
        usleep(5000000);
        $callback(25);

        //task 4
        usleep(3000000);
        $callback(25);

        //at this point the progress bar is finished so you can return whatever is appropriate here
        return true;
    }

答案 1 :(得分:0)

您似乎将100设置为没有任何其他内容的任意数字。

您可以在doStuff中调用getter来允许您更新父命令。

$progress = $this->getHelperSet()->get('progress');

$progress->start($this->output, 100);

$i = 0;
while ($i++ < 100) {
    if (null === $this->doStuff() || $this->doStuff()->getCount() >= $i) {
        $progress->advance();
    }
}