Update der Finanzamtnummern in Hamburg
[kivitendo-erp.git] / SL / Controller / Helper / ParseFilter.pm
index 3753d16..3bf1b65 100644 (file)
@@ -20,11 +20,13 @@ my %filters = (
 );
 
 my %methods = (
 );
 
 my %methods = (
-  lt     => sub { +{ lt    => $_[0] } },
-  gt     => sub { +{ gt    => $_[0] } },
-  ilike  => sub { +{ ilike => $_[0] } },
-  like   => sub { +{ like  => $_[0] } },
   enable => sub { ;;;; },
   enable => sub { ;;;; },
+  map {
+    # since $_ is an alias it can't be used in a closure. even "".$_ or "$_"
+    # does not work, we need a real copy.
+    my $_copy = "$_";
+    $_   => sub { +{ $_copy    => $_[0] } },
+  } qw(similar match imatch regex regexp like ilike rlike is is_not ne eq lt gt le ge),
 );
 
 sub parse_filter {
 );
 
 sub parse_filter {
@@ -36,7 +38,7 @@ sub parse_filter {
 
   my $query = _parse_filter($flattened, %params);
 
 
   my $query = _parse_filter($flattened, %params);
 
-  _launder_keys($filter) unless $params{no_launder};
+  _launder_keys($filter, $params{launder_to}) unless $params{no_launder};
 
   return
     ($query   && @$query   ? (query => $query) : ()),
 
   return
     ($query   && @$query   ? (query => $query) : ()),
@@ -44,23 +46,27 @@ sub parse_filter {
 }
 
 sub _launder_keys {
 }
 
 sub _launder_keys {
-  my ($filter) = @_;
+  my ($filter, $launder_to) = @_;
+  $launder_to ||= $filter;
   return unless ref $filter eq 'HASH';
   return unless ref $filter eq 'HASH';
-  my @keys = keys %$filter;
-  for my $key (@keys) {
+  for my $key (keys %$filter) {
     my $orig = $key;
     $key =~ s/:/_/g;
     my $orig = $key;
     $key =~ s/:/_/g;
-    $filter->{$key} = $filter->{$orig};
-    _launder_keys($filter->{$key});
+    if ('' eq ref $filter->{$orig}) {
+      $launder_to->{$key} = $filter->{$orig};
+    } elsif ('ARRAY' eq ref $filter->{$orig}) {
+      $launder_to->{$key} = [ @{ $filter->{$orig} } ];
+    } else {
+      $launder_to->{$key} ||= { };
+      _launder_keys($filter->{$key}, $launder_to->{$key});
+    }
   };
   };
-
-  return $filter;
 }
 
 sub _pre_parse {
   my ($filter, $with_objects, $prefix, %params) = @_;
 
 }
 
 sub _pre_parse {
   my ($filter, $with_objects, $prefix, %params) = @_;
 
-  return () unless 'HASH'  eq ref $filter;
+  return (undef, $with_objects) unless 'HASH'  eq ref $filter;
   $with_objects ||= [];
 
   my @result;
   $with_objects ||= [];
 
   my @result;
@@ -70,7 +76,7 @@ sub _pre_parse {
     if ('HASH' eq ref $value) {
       my ($query, $more_objects) = _pre_parse($value, $with_objects, _prefix($prefix, $key));
       push @result,        @$query if $query;
     if ('HASH' eq ref $value) {
       my ($query, $more_objects) = _pre_parse($value, $with_objects, _prefix($prefix, $key));
       push @result,        @$query if $query;
-      push @$with_objects, $key, ($more_objects ? @$more_objects : ());
+      push @$with_objects, _prefix($prefix, $key), ($more_objects ? @$more_objects : ());
     } else {
       push @result, _prefix($prefix, $key) => $value;
     }
     } else {
       push @result, _prefix($prefix, $key) => $value;
     }
@@ -207,18 +213,38 @@ and later
 The special empty method will be used to set the method for the previous
 method-less input.
 
 The special empty method will be used to set the method for the previous
 method-less input.
 
-=item Laundering filter
+=back
+
+=head1 LAUNDERING
 
 Unfortunately Template cannot parse the postfixes if you want to
 rerender the filter. For this reason all colons filter keys are by
 
 Unfortunately Template cannot parse the postfixes if you want to
 rerender the filter. For this reason all colons filter keys are by
-default laundered into underscores. If you don't want this to happen
-pass C<< no_launder => 1 >> as a parameter. A full select_tag then
-loks like this:
+default laundered into underscores, so you can use them like this:
 
   [% L.input_tag('filter.price:number::lt', filter.price_number__lt) %]
 
 
   [% L.input_tag('filter.price:number::lt', filter.price_number__lt) %]
 
+All of your original entries will stay intactg. If you don't want this to
+happen pass C<< no_launder => 1 >> as a parameter.  Additionally you can pass a
+different target for the laundered values with the C<launder_to>  parameter. It
+takes an hashref and will deep copy all values in your filter to the target. So
+if you have a filter that looks liek this:
 
 
-=back
+  $filter = {
+    'price:number::lt' => '2,30',
+    'closed            => '1',
+  }
+
+and parse it with
+
+  parse_filter($filter, launder_to => $laundered_filter = { })
+
+the original filter will be unchanged, and C<$laundered_filter> will end up
+like this:
+
+  $filter = {
+    'price_number__lt' => '2,30',
+    'closed            => '1',
+  }
 
 =head1 FILTERS (leading with :)
 
 
 =head1 FILTERS (leading with :)