Merge branch 'master' into eval-code
authorDobrica Pavlinusic <dpavlin@rot13.org>
Thu, 17 Jun 2010 14:27:51 +0000 (16:27 +0200)
committerDobrica Pavlinusic <dpavlin@rot13.org>
Thu, 17 Jun 2010 14:27:51 +0000 (16:27 +0200)
README
lib/MojoFacets/Data.pm
public/js/jquery.textarea_grow.js [new file with mode: 0644]
public/mojo_facets.css
templates/data/items/table.html.ep

diff --git a/README b/README
index edbdb06..750c6f8 100644 (file)
--- a/README
+++ b/README
@@ -42,3 +42,19 @@ any other dataset which has same unique values you can use helper script:
   $ ./script/actions-to-changes /data/mojo_facets/*
 
 
+Modify your data using perl snippets
+
+Experimental REPL console supports perl snippets which get $rec hash which is one
+element from your dataset. All values are repetable, so you always have to create
+array of values if you are creating new columns, even for single value.
+
+* generate new columns with number of elements in some other column
+
+  $rec->{count} = [ $#{ $rec->{original} } + 1 ];
+
+* generate century column from year
+
+  foreach my $year ( @{ $rec->{Year} } ) {
+    push @{ $rec->{century} }, int($year/100)+1;
+  }
+
index c2283b8..e3cfa46 100644 (file)
@@ -372,7 +372,7 @@ sub _param_scalar {
                $self->session($name => $scalar);
        }
 
-       warn "# _perm_scalar $name ",dump $scalar;
+       warn "# _param_scalar $name ",dump $scalar;
        return $scalar;
 }
 
@@ -605,17 +605,58 @@ sub items {
 
        warn "all_filters $all_filters produced ", $#$filtered + 1, " items\n" if $filtered;
 
-       my $sorted_items;
        my $data = $self->_loaded('data');
+
+       my $code = $self->_param_scalar('code','');
+       $code =~ s{\n+$}{}s;
+
+       my $commit = $self->param('commit');
+       my $test = $self->param('test');
+
+       if ( $code && ( $test || $commit ) ) {
+               # XXX find columns used in code snippet and show them to user
+               foreach my $column ( $code =~ m/\$rec->{(.+?)}/g ) {
+                       if ( $column =~ s/^(['"])// ) {
+                               $column =~ s/$1$//;
+                       }
+                       next if grep { /$column/ } @columns;
+                       unshift @columns, $column;
+                       if ( $commit ) {
+                               $self->session('columns', [ @columns ]);
+                               $loaded->{$path}->{columns} = [ @columns ];
+                       }
+               }
+       }
+
+       if ( $commit ) {
+               warn "# commit on ", $#$filtered + 1, " items:\n$code\n";
+               foreach ( 0 .. $#$filtered ) {
+                       my $i = $filtered->[$_];
+                       my $rec = $data->{items}->[$i];
+                       eval $code;
+               }
+       }
+
+       my $sorted_items;
        my $from_end = $sort eq 'd' ? $#$filtered : 0;
        foreach ( 0 .. $limit ) {
                my $i = $_ + $offset;
                last unless defined $filtered->[$i];
                $i = $from_end - $i if $from_end;
                my $id = $filtered->[$i];
-               push @$sorted_items,
-               my $item = $data->{items}->[ $id ];
-               $item->{_row_id} ||= $id;
+               my $rec = $data->{items}->[ $id ];
+               $rec->{_row_id} ||= $id;
+               if ( $code && $test ) {
+                       $rec = Storable::dclone $rec;
+                       eval $code;
+                       if ( $@ ) {
+                               warn "ERROR evaling\n$code\n$@";
+                               $self->stash('eval_error', $@) if $@;
+                       } else {
+                               warn "EVAL ",dump($rec);
+                       }
+               }
+               push @$sorted_items, $rec;
        }
 
        warn "# sorted_items ", $#$sorted_items + 1, " offset $offset limit $limit order $sort";
@@ -629,6 +670,7 @@ sub items {
                rows => $#$filtered + 1,
                numeric => { map { $_, $self->_is_numeric($_) } @columns },
                filters => $self->_current_filters,
+               code => $code,
        );
 
 }
diff --git a/public/js/jquery.textarea_grow.js b/public/js/jquery.textarea_grow.js
new file mode 100644 (file)
index 0000000..a07ab75
--- /dev/null
@@ -0,0 +1,17 @@
+jQuery.fn.textarea_grow = function(){
+       return this.each(function(){
+               var rows = this.rows;
+               console.debug( 'textarea_grow', rows, this );
+               var grow = function(ta) {
+               var lines = ta.value.split('\n').length;
+                       if ( lines != rows ) {
+                               ta.rows = lines;
+                               rows    = lines;
+                               console.debug('keyup', lines, rows, ta );
+                       }
+               };
+               grow(this);
+               this.onkeyup = function() { grow(this) };
+       });
+};
+
index b67da0f..4564c1c 100644 (file)
@@ -160,6 +160,21 @@ form.action_filter {
        color: #444;
 }
 
+/* items/table */
+
+form#eval {
+       position: fixed;
+       bottom: 0;
+       left: 0;
+       width: 100%;
+       z-index: 10;
+       background: #eee;
+}
+
+form#eval textarea {
+       width: 100%;
+}
+
 /* items/list.html.ep */
 a.facet {
        font-family: monospace;
@@ -204,10 +219,15 @@ tr.hidden {
        display: none;
 }
 
-.alert {
+.alert, .error {
        border: 0.3em dashed #f00;
        background: #ffc;
+       text-align: center;
+}
+
+.alert {
        padding: 1em;
        margin: 1em;
-       text-align: center;
 }
+
+
index b55d7c0..e0478b5 100644 (file)
@@ -48,5 +48,24 @@ filter
 
 </table>
 
+<form id=eval method=post>
+% if ( my $error = stash('eval_error') ) {
+<div class=error><%= $error %></div>
+% }
+% my $rows = scalar split(/\n/,$code);
+<textarea name=code rows=<%= $rows %>>
+<%= $code %>
+</textarea>
+<input name=test   type=submit value="Test code">
+<input name=commit type=submit value="Commit changes">
+</form>
+
 <script type="text/javascript" src="/edit_table.js"></script>
+<script type="text/javascript" src="/js/jquery.textarea_grow.js"></script>
+<script type="text/javascript">
+
+$(document).ready( function(){
+       $('form#eval textarea').textarea_grow();
+});
 
+</script>