+our ($out, $key,$value);
+
+our $lookup_path_col;
+our $on;
+
+sub __commit_begin {
+ warn "__commit_begin";
+ $lookup_path_col = undef;
+ $on = undef;
+}
+
+sub __commit_end {
+ warn "__commit_end";
+ $lookup_path_col = undef; # cleanup memory
+ $on = undef;
+}
+
+sub lookup {
+ warn "# lookup ",dump @_;
+ my ( $vals, $on_path, $on_col, $code, $stat_code ) = @_;
+ die "code is not sub{ ... } but ", dump $code unless ref $code eq 'CODE';
+
+ if ( ! exists $loaded->{$on_path} ) {
+ my @possible_paths = grep { /\Q$on_path\E/ } keys %$loaded;
+ die "more than one dataset available for '$on_path' ",dump @possible_paths if $#possible_paths > 0;
+ $on_path = shift @possible_paths;
+ warn "## fuzzy selected path $on_path";
+ }
+
+ my $items = $loaded->{$on_path}->{data}->{items} || die "no items for $on_path";
+
+ if ( ! exists $lookup_path_col->{$on_path}->{$on_col} ) {
+ warn "create lookup_path_col $on_path $on_col";
+ foreach my $i ( 0 .. $#$items ) {
+ my $item = $items->[$i];
+ if ( exists $item->{$on_col} ) {
+ if ( ref $item->{$on_col} eq 'ARRAY' ) {
+ foreach my $v ( @{ $item->{$on_col} } ) {
+ push @{ $lookup_path_col->{$on_path}->{$on_col}->{$v} }, $i;
+ }
+ } elsif ( ! ref $item->{$on_col} ) { # scalar
+ my $v = $item->{$on_col};
+ push @{ $lookup_path_col->{$on_path}->{$on_col}->{$v} }, $i;
+ } else {
+ die "unknown type of ",dump $item->{$on_col};
+ }
+ }
+ }
+ warn "XXX ",dump $lookup_path_col->{$on_path}->{$on_col} if $ENV{DEBUG};
+ }
+
+ my $stat;
+ $stat = Statistics::Descriptive::Full->new() if $stat_code;
+
+ foreach my $v ( ref $vals eq 'ARRAY' ? @$vals : ( $vals ) ) {
+ foreach my $i ( @{ $lookup_path_col->{$on_path}->{$on_col}->{$v} } ) {
+ $on = $items->[$i];
+ warn "XXX lookup code $v $i ",dump $on if $ENV{DEBUG};
+ $code->($stat);
+ }
+ $stat_code->( $stat ) if $stat_code;
+ }
+}
+
+sub __commit_path_code {
+ my ( $path, $i, $code, $commit_changed ) = @_;
+
+ my $items = $loaded->{$path}->{data}->{items} || die "no items for $path";
+ my $row = $items->[$i];
+ my $update;
+ eval $code;
+ foreach ( keys %$update ) {
+ $$commit_changed->{$_}++;
+ $loaded->{$path}->{data}->{items}->[$i]->{$_} = $update->{$_};
+ }
+ #warn "__commit_path_code $path $i ",dump( $update );
+}
+
+# uses templates/admin.html.ep
+sub _switch_dataset {
+ my $self = shift;
+
+ my $datasets;
+
+ foreach my $path ( keys %$loaded ) {
+ next unless exists $loaded->{$path}->{data};
+ push @$datasets, $path;
+ }
+
+ warn "# datasets ",dump($datasets);
+
+ $self->stash( 'datasets' => $datasets );
+}
+