Merge branch 'b-3.6.1' of ../kivitendo-erp_20220811
[kivitendo-erp.git] / modules / fallback / Exception / Lite.pm
diff --git a/modules/fallback/Exception/Lite.pm b/modules/fallback/Exception/Lite.pm
deleted file mode 100644 (file)
index 5f467e6..0000000
+++ /dev/null
@@ -1,527 +0,0 @@
-# Copyright (c) 2010 Elizabeth Grace Frank-Backman.
-# All rights reserved.
-# Liscenced under the "Artistic Liscence"
-# (see http://dev.perl.org/licenses/artistic.html)
-
-use 5.8.8;
-use strict;
-use warnings;
-use overload;
-
-package Exception::Lite;
-our @ISA = qw(Exporter);
-our @EXPORT_OK=qw(declareExceptionClass isException isChainable
-                  onDie onWarn);
-our %EXPORT_TAGS
-  =( common => [qw(declareExceptionClass isException isChainable)]
-     , all => [@EXPORT_OK]
-   );
-my $CLASS='Exception::Lite';
-
-#------------------------------------------------------------------
-
-our $STRINGIFY=3;
-our $FILTER=1;
-our $UNDEF='<undef>';
-our $TAB=3;
-our $LINE_LENGTH=120;
-
-# provide command line control over amount and layout of debugging
-# information, e.g. perl -mException::Lite=STRINGIFY=4
-
-sub import {
-  Exception::Lite->export_to_level(1, grep {
-    if (/^(\w+)=(.*)$/) {
-      my $k = $1;
-      my $v = $2;
-      if ($k eq 'STRINGIFY')        { $STRINGIFY=$v;
-      } elsif ($k eq 'FILTER')      { $FILTER=$v;
-      } elsif ($k eq 'LINE_LENGTH') { $LINE_LENGTH=$v;
-      } elsif ($k eq 'TAB')         { $TAB=$v;
-      }
-      0;
-    } else {
-      1;
-    }
-  } @_);
-}
-
-#------------------------------------------------------------------
-# Note to source code divers: DO NOT USE THIS. This is intended for
-# internal use but must be declared with "our" because we need to
-# localize it.  This is an implementation detail and cannot be relied
-# on for future releases.
-
-our $STACK_OFFSET=0;
-
-#------------------------------------------------------------------
-
-use Scalar::Util ();
-use constant EVAL => '(eval)';
-
-#==================================================================
-# EXPORTABLE FUNCTIONS
-#==================================================================
-
-sub declareExceptionClass {
-  my ($sClass, $sSuperClass, $xFormatRule, $bCustomizeSubclass) = @_;
-  my $sPath = $sClass; $sPath =~ s/::/\//g; $sPath .= '.pm';
-  if ($INC{$sPath}) {
-    # we want to start with the caller's frame, not ours
-    local $STACK_OFFSET = $STACK_OFFSET + 1;
-    die 'Exception::Lite::Any'->new("declareExceptionClass failed: "
-                                    . "$sClass is already defined!");
-    return undef;
-  }
-
-  my $sRef=ref($sSuperClass);
-  if ($sRef) {
-    $bCustomizeSubclass = $xFormatRule;
-    $xFormatRule = $sSuperClass;
-    $sSuperClass=undef;
-  } else {
-    $sRef = ref($xFormatRule);
-    if (!$sRef && defined($xFormatRule)) {
-      $bCustomizeSubclass = $xFormatRule;
-      $xFormatRule = undef;
-    }
-  }
-
-  # set up things dependent on whether or not the class has a
-  # format string or expects a message for each instance
-
-  my ($sLeadingParams, $sAddOrOmit, $sRethrowMsg, $sMakeMsg);
-  my $sReplaceMsg='';
-
-  if ($sRef) {
-    $sLeadingParams='my $e; $e=shift if ref($_[0]);';
-    $sAddOrOmit='added an unnecessary message or format';
-    $sRethrowMsg='';
-
-    #generate format rule
-    $xFormatRule=$xFormatRule->($sClass) if ($sRef eq 'CODE');
-
-    my $sFormat= 'q{' . $xFormatRule->[0] . '}';
-    if (scalar($xFormatRule) == 1) {
-      $sMakeMsg='my $msg='.$sFormat;
-    } else {
-      my $sSprintf = 'Exception::Lite::_sprintf(' . $sFormat
-        . ', map {defined($_)?$_:\''. $UNDEF .'\'} @$h{qw('
-        . join(' ', @$xFormatRule[1..$#$xFormatRule]) . ')});';
-      $sMakeMsg='my $msg='.$sSprintf;
-      $sReplaceMsg='$_[0]->[0]='.$sSprintf;
-    }
-
-  } else {
-    $sLeadingParams = 'my $e=shift; my $msg;'.
-      'if(ref($e)) { $msg=shift; $msg=$e->[0] if !defined($msg);}'.
-      'else { $msg=$e;$e=undef; }';
-    $sAddOrOmit='omitted a required message';
-    $sRethrowMsg='my $msg=shift; $_[0]->[0]=$msg if defined($msg);';
-    $sMakeMsg='';
-  }
-
-  # put this in an eval so that it doesn't cause parse errors at
-  # compile time in no-threads versions of Perl
-
-  my $sTid = eval q{defined(&threads::tid)?'threads->tid':'undef'};
-
-  my $sDeclare = "package $sClass;".
-    'sub new { my $cl=shift;'.  $sLeadingParams .
-      'my $st=Exception::Lite::_cacheStackTrace($e);'.
-      'my $h= Exception::Lite::_shiftProperties($cl' .
-         ',$st,"'.$sAddOrOmit.'",@_);' . $sMakeMsg .
-      'my $self=bless([$msg,$h,$st,$$,'.$sTid.',$e,[]],$cl);';
-
-  # the remainder depends on the type of subclassing
-
-  if ($bCustomizeSubclass) {
-    $sDeclare .= '$self->[7]={}; $self->_new(); return $self; }'
-      . 'sub _p_getSubclassData { $_[0]->[7]; }';
-  } else {
-    $sDeclare .= 'return $self;}'.
-    'sub replaceProperties {'.
-       'my $h={%{$_[0]->[1]},%{$_[1]}}; $_[0]->[1]=$h;'.$sReplaceMsg.
-    '}'.
-    'sub rethrow {' .
-      'my $self=shift;' . $sRethrowMsg .
-      'Exception::Lite::_rethrow($self,"'.$sAddOrOmit.'",@_)' .
-    '}';
-
-    unless (isExceptionClass($sSuperClass)) {
-      $sDeclare .=
-        'sub _getInterface { \'Exception::Lite\' }' .
-        'sub getMessage { $_[0]->[0] };' .
-        'sub getProperty { $_[0]->[1]->{$_[1]} }' .
-        'sub isProperty { exists($_[0]->[1]->{$_[1]})?1:0 }' .
-        'sub getStackTrace { $_[0]->[2] }' .
-        'sub getFrameCount { scalar(@{$_[0]->[2]}); }' .
-        'sub getFile { $_[0]->[2]->[ $_[1]?$_[1]:0 ]->[0] };' .
-        'sub getLine { $_[0]->[2]->[ $_[1]?$_[1]:0 ]->[1] };' .
-        'sub getSubroutine { $_[0]->[2]->[ $_[1]?$_[1]:0 ]->[2] };' .
-        'sub getArgs { $_[0]->[2]->[ $_[1]?$_[1]:0 ]->[3] };' .
-        'sub getPackage {$_[0]->[2]->[-1]->[2] =~ /(\w+)>$/;$1}'.
-        'sub getPid { $_[0]->[3] }' .
-        'sub getTid { $_[0]->[4] }' .
-        'sub getChained { $_[0]->[5] }' .
-        'sub getPropagation { $_[0]->[6]; }' .
-        'use overload '.
-           'q{""} => \&Exception::Lite::_dumpMessage ' .
-           ', q{0+} => \&Exception::Lite::_refaddr, fallback=>1;' .
-        'sub PROPAGATE { push @{$_[0]->[6]},[$_[1],$_[2]]; $_[0]}';
-    }
-  }
-  $sDeclare .= 'return 1;';
-
-  local $SIG{__WARN__} = sub {
-    my ($p,$f,$l) = caller(2);
-    my $s=$_[0]; $s =~ s/at \(eval \d+\)\s+line\s+\d+\.//m;
-    print STDERR "$s in declareExceptionClass($sClass,...) "
-      ."in file $f, line $l\n";
-  };
-
-  eval $sDeclare or do {
-    my ($p,$f,$l) = caller(1);
-    print STDERR "Can't create class $sClass at file $f, line $l\n";
-    if ($sClass =~ /\w:\w/) {
-      print STDERR "Bad class name: "
-        ."At least one ':' is not doubled\n";
-    } elsif ($sClass !~ /^\w+(?:::\w+)*$/) {
-      print STDERR "Bad class name: $sClass\n";
-    } else {
-      $sDeclare=~s/(sub |use )/\n$1/g; print STDERR "$sDeclare\n";
-    }
-  };
-
-  # this needs to be separate from the eval, otherwise it never
-  # ends up in @INC or @ISA, at least in Perl 5.8.8
-  $INC{$sPath} = __FILE__;
-  eval "\@${sClass}::ISA=qw($sSuperClass);" if $sSuperClass;
-
-  return $sClass;
-}
-
-#------------------------------------------------------------------
-
-sub isChainable { return ref($_[0])?1:0; }
-
-#------------------------------------------------------------------
-
-sub isException {
-  my ($e, $sClass) = @_;
-  my $sRef=ref($e);
-  return !defined($sClass)
-    ? ($sRef ? isExceptionClass($sRef) : 0)
-    : $sClass eq ''
-       ? ($sRef eq '' ? 1 : 0)
-       : ($sRef eq '')
-            ? 0
-            : $sRef->isa($sClass)
-               ?1:0;
-}
-
-#------------------------------------------------------------------
-
-sub isExceptionClass {
-  return defined($_[0]) && $_[0]->can('_getInterface')
-    && ($_[0]->_getInterface() eq __PACKAGE__) ? 1 : 0;
-}
-
-#------------------------------------------------------------------
-
-sub onDie {
-  my $iStringify = $_[0];
-  $SIG{__DIE__} = sub {
-    $Exception::Lite::STRINGIFY=$iStringify;
-    warn 'Exception::Lite::Any'->new('Unexpected death:'.$_[0])
-      unless $^S || isException($_[0]);
-  };
-}
-
-#------------------------------------------------------------------
-
-sub onWarn {
-  my $iStringify = $_[0];
-  $SIG{__WARN__} = sub {
-    $Exception::Lite::STRINGIFY=$iStringify;
-    print STDERR 'Exception::Lite::Any'->new("Warning: $_[0]");
-  };
-}
-
-#==================================================================
-# PRIVATE SUBROUTINES
-#==================================================================
-
-#------------------------------------------------------------------
-
-sub _cacheCall {
-  my $iFrame = $_[0];
-
-  my @aCaller;
-  my $aArgs;
-
-  # caller populates @DB::args if called within DB package
-  eval {
-    # this 2 line wierdness is needed to prevent Module::Build from finding
-    # this and adding it to the provides list.
-    package
-      DB;
-
-    #get rid of eval and call to _cacheCall
-    @aCaller = caller($iFrame+2);
-
-    # mark leading undefined elements as maybe shifted away
-    my $iDefined;
-    if ($#aCaller < 0) {
-      @DB::args=@ARGV;
-    }
-    $aArgs = [  map {
-      defined($_)
-        ? do {$iDefined=1;
-              "'$_'" . (overload::Method($_,'""')
-                        ? ' ('.overload::StrVal($_).')':'')}
-          : 'undef' . (defined($iDefined)
-                       ? '':'  (maybe shifted away?)')
-        } @DB::args];
-  };
-
-  return $#aCaller < 0 ? \$aArgs : [ @aCaller[0..3], $aArgs ];
-}
-
-#------------------------------------------------------------------
-
-sub _cacheStackTrace {
-  my $e=$_[0]; my $st=[];
-
-  # set up initial frame
-  my $iFrame= $STACK_OFFSET + 1; # call to new
-  my $aCall = _cacheCall($iFrame++);
-  my ($sPackage, $iFile, $iLine, $sSub, $sArgs) = @$aCall;
-  my $iLineFrame=$iFrame;
-
-  $aCall =  _cacheCall($iFrame++);  #context of call to new
-  while (ref($aCall) ne 'REF') {
-    $sSub  = $aCall->[3];  # subroutine containing file,line
-    $sArgs = $aCall->[4];  # args used to call $sSub
-
-    #print STDERR "debug-2: package=$sPackage file=$iFile line=$iLine"
-    #  ." sub=$sSub, args=@$sArgs\n";
-
-    # in evals we want the line number within the eval, but the
-    # name of the sub in which the eval was located. To get this
-    # we wait to push on the stack until we get an actual sub name
-    # and we avoid overwriting the location information, hence 'ne'
-
-    if (!$FILTER || ($sSub ne EVAL)) {
-      my $aFrame=[ $iFile, $iLine, $sSub, $sArgs ];
-      ($sPackage, $iFile, $iLine) = @$aCall;
-      $iLineFrame=$iFrame;
-
-      my $sRef=ref($FILTER);
-      if ($sRef eq 'CODE') {
-        my $x = $FILTER->(@$aFrame, $iFrame, $iLineFrame);
-        if (ref($x) eq 'ARRAY') {
-          $aFrame=$x;
-        } elsif (!$x) {
-          $aFrame=undef;
-        }
-      } elsif (($sRef eq 'ARRAY') && ! _isIgnored($sSub, $FILTER)) {
-        $aFrame=undef;
-      } elsif (($sRef eq 'Regexp') && !_isIgnored($sSub, [$FILTER])) {
-        $aFrame=undef;
-      }
-      push(@$st, $aFrame) if $aFrame;
-    }
-
-    $aCall = _cacheCall($iFrame++);
-  }
-
-  push @$st, [ $iFile, $iLine, "<package: $sPackage>", $$aCall ];
-  if ($e) { my $n=$#{$e->[2]}-$#$st;$e->[2]=[@{$e->[2]}[0..$n]]};
-  return $st;
-}
-
-#-----------------------------
-
-sub _isIgnored {
-  my ($sSub, $aIgnore) = @_;
-  foreach my $re (@$aIgnore) { return 1 if $sSub =~ $re; }
-  return 0;
-}
-
-#------------------------------------------------------------------
-
-sub _dumpMessage {
-  my ($e, $iDepth) = @_;
-
-  my $sMsg = $e->getMessage();
-  return $sMsg unless $STRINGIFY;
-  if (ref($STRINGIFY) eq 'CODE') {
-    return $STRINGIFY->($sMsg);
-  }
-
-  $iDepth = 0 unless defined($iDepth);
-  my $sIndent = ' ' x ($TAB*$iDepth);
-  $sMsg = "\n${sIndent}Exception! $sMsg";
-  return $sMsg if $STRINGIFY == 0;
-
-  my ($sThrow, $sReach);
-  my $sTab = ' ' x $TAB;
-
-  $sIndent.= $sTab;
-  if ($STRINGIFY > 2) {
-    my $aPropagation = $e->getPropagation();
-    for (my $i=$#$aPropagation; $i >= 0; $i--) {
-      my ($f,$l) = @{$aPropagation->[$i]};
-      $sMsg .= "\n${sIndent}rethrown at file $f, line $l";
-    }
-    $sMsg .= "\n";
-    $sThrow='thrown  ';
-    $sReach='reached ';
-  } else {
-    $sThrow='';
-    $sReach='';
-  }
-
-  my $st=$e->getStackTrace();
-  my $iTop = scalar @$st;
-
-  for (my $iFrame=0; $iFrame<$iTop; $iFrame++) {
-    my ($f,$l,$s,$aArgs) = @{$st->[$iFrame]};
-
-    if ($iFrame) {
-      #2nd and following stack frame
-      my $sVia="${sIndent}${sReach}via file $f, line $l";
-      my $sLine="$sVia in $s";
-      $sMsg .= (length($sLine)>$LINE_LENGTH
-                ? "\n$sVia\n$sIndent${sTab}in $s" : "\n$sLine");
-    } else {
-      # first stack frame
-      my $tid=$e->getTid();
-      my $sAt="${sIndent}${sThrow}at  file $f, line $l";
-      my $sLine="$sAt in $s";
-      $sMsg .= (length($sLine)>$LINE_LENGTH
-                ? "\n$sAt\n$sIndent${sTab}in $s" : "\n$sLine")
-        . ", pid=" . $e->getPid() . (defined($tid)?", tid=$tid":'');
-
-      return "$sMsg\n" if $STRINGIFY == 1;
-    }
-
-    if ($STRINGIFY > 3) {
-      my $bTop = ($iFrame+1) == $iTop;
-      my $sVar= ($bTop && !$iDepth) ? '@ARGV' : '@_';
-      my $bMaybeEatenByGetOpt = $bTop && !scalar(@$aArgs)
-        && exists($INC{'Getopt/Long.pm'});
-
-      my $sVarIndent = "\n${sIndent}" . (' ' x $TAB);
-      my $sArgPrefix = "${sVarIndent}".(' ' x length($sVar)).' ';
-      if ($bMaybeEatenByGetOpt) {
-        $sMsg .= $sArgPrefix . $sVar
-          . '()    # maybe eaten by Getopt::Long?';
-      } else {
-        my $sArgs = join($sArgPrefix.',', @$aArgs);
-        $sMsg .= "${sVarIndent}$sVar=($sArgs";
-        $sMsg .= $sArgs ? "$sArgPrefix)" : ')';
-      }
-    }
-  }
-  $sMsg.="\n";
-  return $sMsg if $STRINGIFY == 2;
-
-  my $eChained = $e->getChained();
-  if (defined($eChained)) {
-    my $sTrigger = isException($eChained)
-      ? _dumpMessage($eChained, $iDepth+1)
-      : "\n${sIndent}$eChained\n";
-    $sMsg .= "\n${sIndent}Triggered by...$sTrigger";
-  }
-  return $sMsg;
-}
-
-#------------------------------------------------------------------
-
-# refaddr has a prototype($) so we can't use it directly as an
-# overload operator: it complains about being passed 3 parameters
-# instead of 1.
-sub _refaddr { Scalar::Util::refaddr($_[0]) };
-
-#------------------------------------------------------------------
-
-sub _rethrow {
-  my $self = shift; my $sAddOrOmit = shift;
-  my ($p,$f,$l)=caller(1);
-  $self->PROPAGATE($f,$l);
-
-  if (@_%2) {
-    warn sprintf('bad parameter list to %s->rethrow(...)'
-      .'at file %d, line %d: odd number of elements in property-value '
-      .'list, property value has no property name and will be '
-      ."discarded (common causes: you have %s string)\n"
-      ,$f, $l, $sAddOrOmit);
-    shift @_;
-  }
-  $self->replaceProperties({@_}) if (@_);
-  return $self;
-}
-
-#------------------------------------------------------------------
-# Traps warnings and reworks them so that they tell the user how
-# to fix the problem rather than obscurely complain about an
-# invisible sprintf with uninitialized values that seem to come from
-# no where (and make Exception::Lite look like it is broken)
-
-sub _sprintf {
-  my $sMsg;
-  my $sWarn;
-
-  {
-    local $SIG{__WARN__} = sub { $sWarn=$_[0] if !defined($sWarn) };
-
-    # sprintf has prototype ($@)
-    my $sFormat = shift;
-    $sMsg = sprintf($sFormat, @_);
-  }
-
-  if (defined($sWarn)) {
-    my $sReason='';
-    my ($f, $l, $s) = (caller(1))[1,2,3];
-    $s =~ s/::(\w+)\z/->$1/;
-    $sWarn =~ s/sprintf/$s/;
-    $sWarn =~ s/\s+at\s+[\w\/\.]+\s+line\s+\d+\.\s+\z//;
-    if ($sWarn
-        =~ m{^Use of uninitialized value in|^Missing argument}) {
-      my $p=$s; $p =~ s/->\w+\z//;
-      $sReason ="\n     Most likely cause: "
-        . "Either you are missing property-value pairs needed to"
-        . "build the message or your exception class's format"
-        . "definition mistakenly has too many placeholders "
-        . "(e.g. %s,%d,etc)\n";
-    }
-    warn "$sWarn called at file $f, line $l$sReason\n";
-  }
-  return $sMsg;
-}
-
-#------------------------------------------------------------------
-
-sub _shiftProperties {
-  my $cl= shift;  my $st=shift;  my $sAddOrOmit = shift;
-  if (@_%2) {
-    $"='|';
-    warn sprintf('bad parameter list to %s->new(...) at '
-      .'file %s, line %d: odd number of elements in property-value '
-      .'list, property value has no property name and will be '
-      .'discarded (common causes: you have %s string -or- you are '
-      ."using a string as a chained exception)\n"
-      ,$cl,$st->[0]->[0],$st->[0]->[1], $sAddOrOmit);
-    shift @_;
-  }
-  return {@_};
-}
-
-#==================================================================
-# MODULE INITIALIZATION
-#==================================================================
-
-declareExceptionClass(__PACKAGE__ .'::Any');
-1;