Как отделить обработку ошибок от бизнес-логики в Perl? - PullRequest
3 голосов
/ 05 октября 2009

Как отделить обработку исключений / обработку ошибок от бизнес-логики? Я пишу код на Perl, а обработка ошибок / исключений и бизнес-логика усложняют понимание кода при просмотре.

Как я могу реорганизовать свой код, чтобы сделать его более читабельным, но при этом обрабатывать ошибки. Также обратите внимание, что я не использую try catch или что-то в этом роде.

Один из наших старших программистов предложил, чтобы мы снова открыли стандартную ошибку ОС и записали там все, и мы могли ее перехватить.

Изменить: вот как я делаю обработку ошибок. У меня много модулей Perl .. так check2.pm

package check2;
sub printData {
      print STDERR "Error Message from sub routine \n";
    }
    1;

и я использую это так в моем скрипте Perl, check.pl

В моем Perl-скрипте

#!/usr/bin/perl
use LoadModules;
use strict;
use warnings;

load check2;

my $stderrholder;
local *SAVEERR;

# First, save existing STDERR
open SAVEERR, ">&STDERR" or print "not able to open";
close STDERR;

# Open the STDERR to a variable
open STDERR, ">", \$stderrholder or die "Failed to reopen STDERR $!\n";

#Start of processing

# Now print something to STDERR, redirected to $ stderrholder
print STDERR " Error Message from Main script \n";

check2::printData();

#End of processing

# Now close and restore STDERR to original condition.
close STDERR;
#open STDERR, ">&SAVEERR";

# Now check if there were any processing errors.
if(length($stderrholder)) {
  print "\nProcessing errors\n" ;
if(length($stderrholder)) {
  print "\nProcessing errors\n" ;
  print $stderrholder;
} else {
  print "\nNo Processing errors\n" ;
}

Буду очень признателен, если кто-нибудь поможет мне указать на ошибки в этом.

Ответы [ 3 ]

3 голосов
/ 05 октября 2009

Код, вызывающий ошибку

 sub whatever { 
    die "OH NOES" if an_error($occurred);
 }

Ваша основная программа:

 use Try::Tiny; # essential
 my $logger = anything_you_want;
 try {
     whatever;
 }
 catch {
     $logger->error("Error: $_");
 };

Выбрасывать исключения, когда что-то идет не так. Обрабатывать исключения везде, где это имеет смысл; обычно на верхнем уровне.

Иногда вы можете «исправить» исключение; пример: подключиться к отказоустойчивому серверу, если основной сервер недоступен. В этом случае обработайте отработку отказа где-то на более высоком уровне, чем приложение верхнего уровня, но где-то ближе, чем в функции «подключения»:

sub connect {
    die "Error connecting: ..." if ...;
}

sub make_connection {
   my $connection = try { connect($main_server) };
   $connection ||= try { connect($backup_server) };
   die "Couldn't connect to either server" unless $connection;
   return $connection;
}

В каждом коде верхнего уровня вместо каждой отдельной ошибки соединения вы обрабатываете «Не удалось подключиться ни к одному серверу».

Наконец, вы также можете использовать монаду Error . Это позволяет вам возвращать коды ошибок, но гарантирует, что после ошибки код не будет выполнен. (Этот подход лучше работает для асинхронного кода, основанного на событиях ... но большинство программистов на Perl не любят монады и вместо этого пытаются использовать исключения для всего. Это хорошо, хотя ... исключения - отличный способ обработки ошибок.) 1016 *

0 голосов
/ 05 октября 2009

Делает это очень сложно, как? Можете ли вы привести пример того, что сложно?

Вы можете создавать достаточно читаемый код на Perl при обработке ошибок. Например, open(my $filehandle, '>', $filename) or die "Failed to open $filename" - понятное английское предложение. Кроме того, вы можете использовать autodie , чтобы включить автоматический перехват распространенных ошибок.

Один из наших старших программистов предложил, чтобы мы снова открыли стандартную ошибку ОС и записали там все, и мы могли бы ее перехватить.

Полагаю, это лучше, чем ничего, но не останавливайтесь на достигнутом. Завершение всего кода в цикле while (1) и гигантском try / catch не даст вам ничего сложного, плюс это один огромный запах кода.

Наконец:

обратите внимание, что я не использую try catch или что-то в этом роде.

Почему бы и нет?

0 голосов
/ 05 октября 2009

Хороший вопрос, но я думаю, что, хотя это и усложняет код, вы не должны удалять обработку ошибок из бизнес-логики, потому что часто бывают случаи, когда бизнес-логике нужно знать об ошибке.

Я полагаю, что вы, возможно, захотите пересмотреть свою бизнес-логику, чтобы обработка ошибок была обернута вокруг бизнес-логики. Это может сработать, но я не считаю возможным или даже хорошей идеей постоянно отделять обработку ошибок.

Я считаю, что ответ на ваш вопрос во многом зависит от типа приложения и сложности бизнес-логики.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...