zfcampus / zf-console

Create console applications in PHP
BSD 3-Clause "New" or "Revised" License
64 stars 25 forks source link

Better error handling #37

Open vaclavvanik opened 8 years ago

vaclavvanik commented 8 years ago

Now is little bit tricky to eg. log errors in zf-console.

I like the idea of new error handler in stratigility. Especially error response (message) generation, triggering listeners (useful for logging) etc.

Do you have any idea how this implement in zf-console? Your opinions?

zf2timo commented 8 years ago

This would be a great addition for this project. I've been thinking of a similar feature for a while now - a ConsoleView. My goal is, that the object covers verbosity, colorful output and (Error)Output as well.

Error Handling and Message Output

Your idea to wrap a Error handler around a Dispatcher is great and could be done here.

Verbosity

To provide a configuration of the verbosity by the developer it could be injected as parameter in the constructor of the View class. I think the level could be re-used from the PSR-3.

$view = new View($writer, View::INFO); 

// Somewhere in a Command
public function __invoke(Route $route, Console $console) {
    $this->view->write(View::DEBUG, 'Start processing Foo Action');

    try {
        // ... Do Some Stuff
    } catch (InvalidArgumentException $exception) {
        $this->view->write(View::ERROR , $exception);
    }
    $this->view->write(View::DEBUG, 'End processing Foo Action');
}

As I am thinking about it, the View could accept the Psr\Log\LoggerInterface as a writer to allow an injection of all PSR-3 implementations. A major advantage are the already available implementations to write the messages that we can re-use.

But it would be a conflict with the next feature.

Colorful Output

It is really annoying to read Log-Files that have symbols like this (\e[42m10/\e[41m1). The important information aren't visible anymore because they are hidden in the control characters for the console. On contrary the colors could be really helpful to highlight important information on the console. So the color should be passed into the writer and it's decide itself if the color is used or discarded.

I propose these interface to allow the features:

namespace ZF\Console\View\Writer;

interface WriterInterface
{
    /**
     * @param int $priority Priority of the Message
     * @param string|\Exception|\Throwable $message Message that should be logged
     * @param int|null $color Color code to control the color of the message
     * @param int|null $backgroundColor Color code to control the background color of the message
     */
    public function write($priority, $message, $color = null, $backgroundColor = null);
}

The View Class could look like this:

namespace ZF\Console\View;

class View {

   /**
    * @param WriterInterface $writer Target to write the message
    * @param int $priority Messages with a smaller priority will be discarded
    */
    public function __constuctor(WriterInterface $writer, $priority) 
    {

    }

    /**
     * @param int $priority Priority of the Message
     * @param string|\Exception|\Throwable $message Message that should be logged
     * @param int|null $color Color code to control the color of the message
     * @param int|null $backgroundColor Color code to control the background color of the message
     */
    public function write($priority, $message, $color = null, $backgroundColor = null) 
    {
        if ($this->isPriorityMatched($priority)) {
            $this->writer->write($priority, $message, $color, $backgroundColor);
        }
    }
}

A ServiceFactory for the View could either automatically detect if the current environment supports a TTY or it is defined by the developer in a local Configuration file.

My idea currently does not cover the following things

@vaclavvanik What do you think about this changes? Is there a chance to cover these features in a View Class?