Как перехватить исключения, но заставить perl-скрипт продолжить выполнение?

#perl #exception

#perl #исключение

Вопрос:

У меня есть пакет для исключений, таких как

 package MyExceptions;

use strict;
use warnings;
use Exception::Class (
     'MyExceptions::TestException' => {               
               fields => [qw{message}],
   }  
);

use Moose::Util::TypeConstraints;

class_type 'MyExceptions::TestException';

no Moose::Util::TypeConstraints;
1;
  

В модуле Communicate..Исключение генерируется всякий раз, когда есть ответ сервера как «ОШИБКА»

 if ( $recv_data eq 'ERROR' )  
    {
        MyExceptions::TestException->throw( message => $data );
    }

    elsif ( $recv_data eq 'YES' ) 
    {        
        return $data;
    }
  

Сценарий выглядит примерно так

 eval{
my $num = 0;
my $flag = 0;

    do
    {
        if($num>6)
    {
        $flag = 1;
        print "NOT found";
    }

        my $region = $obj->FindImage('SomeImage');
        my $x = $region->getX;
        my $y = $region->getY;
        if(($x > 0) amp;amp; ($y>0))
        {
            $flag = 1;
            $obj->Command($x,$y);


        }
        else
        {
                    $Obj->Command1('50','2','160','275','160','220');
        }


$num  ;

} while($flag==0);

$num = 0;

return;
};

    if ( my $ex = $@ ) {

        my $e ;

      if ( $e = Exception::Class->caught('MyExceptions::ExecutionException'))
     {       

         print $e->message;
    }

    }
  

В этом случае .. если изображение не найдено, должна быть выполнена команда и снова необходимо выполнить поиск изображения, однако, в случае, если сервер отвечает как «Ошибка», выдается исключение, поэтому скрипт останавливает выполнение, а выполнение команды и следующая итерация поиска изображения не выполняются. Как к этому можно подойти и разрешить?

Спасибо,

Ответ №1:

Прежде всего, вы не можете return в eval . Так что, вероятно, он достигает конца оценки и молча умирает. Я сталкивался с этим раньше… назад, когда я учился не делать этого return из eval . 🙂

В противном случае, насколько я могу видеть, он выполнял бы то, что вы просите. Когда вы завершаете do {} while с помощью eval, вы говорите, что не хотите, чтобы цикл выполнялся снова, если есть исключение. Если вы хотите еще раз попробовать найти изображение, тогда вам нужно выяснить, как обернуть только это чем-то вроде:

 # try
eval {
    my $region = $obj->FindImage( 'SomeImage' );
    ...
};
# catch
if ( my $ex = Exception::Class->caught( 'MyExceptions::ExecutionException' )) { 
    # logic to decide whether or not to find another image
    ...
}
# if we don't die/croak/"throw" in the if.
...