From fc30364efa6a07b2065f0f54e6792f17970535b8 Mon Sep 17 00:00:00 2001 From: Ian Beckwith Date: Tue, 19 Oct 2010 12:39:35 +0100 Subject: [PATCH] debian/control: update long description --- README | 2 + debian/control | 13 ++++++- lib/ID3FS/Path.pm | 1 + lib/ID3FS/Path/Node.pm | 104 +++++++++++++++++++++++++++++-------------------- 4 files changed, 76 insertions(+), 44 deletions(-) diff --git a/README b/README index 505d614..bc26ca2 100644 --- a/README +++ b/README @@ -14,6 +14,8 @@ thrash/OR/rapmetal/AND/NOT/wears-a-red-hat/ prog/AND/decade/1970s/OR/psychedelia/AND/decade/1960s/ location/sweden/AND/screamo/AND/postrock/ +Multiple tags can be stored in the genre tag, separated by commas. + GETTING ID3FS See http://erislabs.net/ianb/projects/id3fs/ diff --git a/debian/control b/debian/control index 935bc6e..4d307d3 100644 --- a/debian/control +++ b/debian/control @@ -11,5 +11,16 @@ Package: id3fs Architecture: all Depends: libfuse-perl, libdbi-perl, libdbd-sqlite3-perl, ${misc:Depends}, ${perl:Depends} Description: FUSE-based filesystem for browsing audio metadata - FIXME + id3fs provides a browsable filesystem of your music files, organised + into sub-directories by id3 tags (or flac/ogg comments). . + id3fs allows you to construct boolean queries from a tag folksonomy + such as: + . + goth/AND/decade/1980s/ + postrock/AND/NOT/rating/terrible/ + thrash/OR/rapmetal/AND/NOT/wears-a-red-hat/ + prog/AND/decade/1970s/OR/psychedelia/AND/decade/1960s/ + location/sweden/AND/screamo/AND/postrock/ + . + Multiple tags can be stored in the genre tag, separated by commas. diff --git a/lib/ID3FS/Path.pm b/lib/ID3FS/Path.pm index 5a5c10e..4286381 100644 --- a/lib/ID3FS/Path.pm +++ b/lib/ID3FS/Path.pm @@ -364,6 +364,7 @@ sub parse if($self->{tagtree}) { # use Data::Dumper; +# print "TREE\n"; # print Dumper $self->{tagtree}; # my ($conditions, @joins)=$self->{tagtree}->to_sql(); # print "CONDITIONS(", scalar(@joins), "): ", $conditions, "\n"; diff --git a/lib/ID3FS/Path/Node.pm b/lib/ID3FS/Path/Node.pm index 478adb3..bdc403f 100644 --- a/lib/ID3FS/Path/Node.pm +++ b/lib/ID3FS/Path/Node.pm @@ -93,6 +93,7 @@ sub to_sql { @outjoins = @joins = ("INNER"); } + if($self->type() ne "boolean") { my $cnt=scalar(@joins)+1; @@ -103,63 +104,80 @@ sub to_sql } return ($str, @outjoins); } - else + + my $left=$self->left(); + my $right=$self->right(); + return ("", @outjoins) unless($left || $right); + my ($leftstr, @leftjoins) = $left->to_sql($hasvals, $not, @joins) if($left); + push(@joins, @leftjoins); + push(@outjoins, @leftjoins); + my $op=$self->name(); + print "op: $op type: ", $self->type(), " not: $not\n"; + if(defined($op)) { - my $left=$self->left(); - my $right=$self->right(); - return ("", @outjoins) unless($left || $right); - my ($leftstr, @leftjoins) = $left->to_sql($hasvals, $not, @joins) if($left); - push(@joins, @leftjoins); - push(@outjoins, @leftjoins); - my $op=$self->name(); - if(defined($op) && $self->type() eq "boolean") + # if we are ANDing, add an inner join + # also if we are NOTing, but we are looking for a tag *value* + if($op eq "AND") { - # if we are ANDing, add an inner join - # also if we are NOTing, but we are looking for a tag *value* - if( ($op eq "AND") || ($hasvals && ($op eq "NOT"))) - { - # hack - if right child is a NOT, we don't need extra join/brackets - # NOT will do the same and we will end up with an extra one - unless($right && $right->name() && $right->name() eq "NOT") - { - push(@joins, "INNER"); - push(@outjoins, "INNER"); - } - } - elsif($op eq "NOT") + print "AND\n"; + # hack - if right child is a NOT, we don't need extra join/brackets + # NOT will do the same and we will end up with an extra one + unless($right && $right->name() && $right->name() eq "NOT") { - $not=1; - push(@joins, "LEFT"); - push(@outjoins, "LEFT"); -# print("LEFT: ", $left->print(), "\n") if ($left); -# print("RIGHT: ", $right->print(), "\n") if($right); + push(@joins, "INNER"); + push(@outjoins, "INNER"); } - elsif($op eq "OR") + } + elsif($op eq "NOT") + { + print "NOT (was $not)\n"; + $not=1; + # as above - if right child is a NOT, we don't need extra join/brackets + # NOT will do the same and we will end up with an extra one + unless($right && $right->name() && $right->name() eq "NOT") { - # if left child is a not, we need an extra (inner) join - if($left && $left->name() && $left->name() eq "NOT") + if($hasvals) { push(@joins, "INNER"); push(@outjoins, "INNER"); } + else + { + push(@joins, "LEFT"); + push(@outjoins, "LEFT"); + } } +# print("LEFT: ", $left->print(), "\n") if ($left); +# print("RIGHT: ", $right->print(), "\n") if($right); } - my ($rightstr, @rightjoins) = $right->to_sql($hasvals, $not, @joins) if($right); - push(@outjoins, @rightjoins); -# print "LEFT (", scalar(@leftjoins), "): $leftstr\n"; -# print "RIGHT (", scalar(@rightjoins), "): $rightstr\n"; - my $str=$leftstr; - $str .= " $op " if($op && !$not); - $str .= $rightstr; - if($op || ($left && $right)) + elsif($op eq "OR") { - $str="(" . $str . ")"; + print "OR\n"; + # if left child is a NOT, we need an extra (inner) join + # unless right child is also a NOT + if(($left && $left->name() && $left->name() eq "NOT") && + !($right && $right->name() && $right->name() eq "NOT")) + { + push(@joins, "INNER"); + push(@outjoins, "INNER"); + } } -# print "STR: $str\n"; -# my @all=(@joins, @rightjoins); -# print "JOINS: RETURN ", scalar(@outjoins), " ALL ", scalar(@all), "\n"; - return($str, @outjoins); } + my ($rightstr, @rightjoins) = $right->to_sql($hasvals, $not, @joins) if($right); + push(@outjoins, @rightjoins); +# print "LEFT (", scalar(@leftjoins), "): $leftstr\n"; +# print "RIGHT (", scalar(@rightjoins), "): $rightstr\n"; + $str=$leftstr; + $str .= " $op " if($op && !$not); + $str .= $rightstr; + if($op || ($left && $right)) + { + $str="(" . $str . ")"; + } +# print "STR: $str\n"; +# my @all=(@joins, @rightjoins); +# print "JOINS: RETURN ", scalar(@outjoins), " ALL ", scalar(@all), "\n"; + return($str, @outjoins); } sub used_tags -- 2.11.0