releasing/cbrtools/perl/Text/Glob.pm
author kelvzhu
Mon, 18 Oct 2010 16:16:46 +0800
changeset 655 3f65fd25dfd4
parent 602 3145852acc89
permissions -rw-r--r--
sync up SVN codes
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
602
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
     1
# Copyright (C) 2002 Richard Clamp.  All Rights Reserved.
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
     2
#
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
     3
# This module is free software; you can redistribute it and/or modify it
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
     4
# under the same terms as Perl itself.
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
     5
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
     6
package Text::Glob;
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
     7
use strict;
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
     8
use Exporter;
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
     9
use vars qw/$VERSION @ISA @EXPORT_OK
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
    10
            $strict_leading_dot $strict_wildcard_slash/;
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
    11
$VERSION = '0.06';
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
    12
@ISA = 'Exporter';
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
    13
@EXPORT_OK = qw( glob_to_regex match_glob );
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
    14
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
    15
$strict_leading_dot    = 1;
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
    16
$strict_wildcard_slash = 1;
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
    17
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
    18
use constant debug => 0;
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
    19
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
    20
sub glob_to_regex {
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
    21
    my $glob = shift;
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
    22
    my ($regex, $in_curlies, $escaping);
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
    23
    local $_;
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
    24
    my $first_byte = 1;
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
    25
    for ($glob =~ m/(.)/gs) {
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
    26
        if ($first_byte) {
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
    27
            if ($strict_leading_dot) {
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
    28
                $regex .= '(?=[^\.])' unless $_ eq '.';
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
    29
            }
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
    30
            $first_byte = 0;
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
    31
        }
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
    32
        if ($_ eq '/') {
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
    33
            $first_byte = 1;
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
    34
        }
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
    35
        if ($_ eq '.' || $_ eq '(' || $_ eq ')' || $_ eq '|' ||
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
    36
            $_ eq '+' || $_ eq '^' || $_ eq '$' ) {
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
    37
            $regex .= "\\$_";
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
    38
        }
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
    39
        elsif ($_ eq '*') {
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
    40
            $regex .= $escaping ? "\\*" :
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
    41
              $strict_wildcard_slash ? "[^/]*" : ".*";
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
    42
        }
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
    43
        elsif ($_ eq '?') {
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
    44
            $regex .= $escaping ? "\\?" :
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
    45
              $strict_wildcard_slash ? "[^/]" : ".";
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
    46
        }
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
    47
        elsif ($_ eq '{') {
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
    48
            $regex .= $escaping ? "\\{" : "(";
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
    49
            ++$in_curlies unless $escaping;
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
    50
        }
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
    51
        elsif ($_ eq '}' && $in_curlies) {
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
    52
            $regex .= $escaping ? "}" : ")";
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
    53
            --$in_curlies unless $escaping;
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
    54
        }
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
    55
        elsif ($_ eq ',' && $in_curlies) {
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
    56
            $regex .= $escaping ? "," : "|";
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
    57
        }
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
    58
        elsif ($_ eq "\\") {
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
    59
            if ($escaping) {
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
    60
                $regex .= "\\\\";
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
    61
                $escaping = 0;
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
    62
            }
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
    63
            else {
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
    64
                $escaping = 1;
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
    65
            }
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
    66
            next;
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
    67
        }
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
    68
        else {
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
    69
            $regex .= $_;
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
    70
            $escaping = 0;
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
    71
        }
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
    72
        $escaping = 0;
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
    73
    }
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
    74
    print "# $glob $regex\n" if debug;
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
    75
    qr/^$regex$/;
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
    76
}
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
    77
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
    78
sub match_glob {
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
    79
    print "# ", join(', ', map { "'$_'" } @_), "\n" if debug;
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
    80
    my $glob = shift;
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
    81
    my $regex = glob_to_regex $glob;
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
    82
    local $_;
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
    83
    grep { $_ =~ $regex } @_;
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
    84
}
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
    85
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
    86
1;
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
    87
__END__
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
    88
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
    89
=head1 NAME
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
    90
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
    91
Text::Glob - match globbing patterns against text
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
    92
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
    93
=head1 SYNOPSIS
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
    94
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
    95
 use Text::Glob qw( match_glob glob_to_regex );
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
    96
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
    97
 print "matched\n" if match_glob( "foo.*", "foo.bar" );
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
    98
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
    99
 # prints foo.bar and foo.baz
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
   100
 my $regex = glob_to_regex( "foo.*" );
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
   101
 for ( qw( foo.bar foo.baz foo bar ) ) {
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
   102
     print "matched: $_\n" if /$regex/;
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
   103
 }
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
   104
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
   105
=head1 DESCRIPTION
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
   106
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
   107
Text::Glob implements glob(3) style matching that can be used to match
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
   108
against text, rather than fetching names from a filesystem.  If you
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
   109
want to do full file globbing use the File::Glob module instead.
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
   110
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
   111
=head2 Routines
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
   112
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
   113
=over
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
   114
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
   115
=item match_glob( $glob, @things_to_test )
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
   116
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
   117
Returns the list of things which match the glob from the source list.
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
   118
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
   119
=item glob_to_regex( $glob )
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
   120
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
   121
Returns a compiled regex which is the equiavlent of the globbing
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
   122
pattern.
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
   123
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
   124
=back
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
   125
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
   126
=head1 SYNTAX
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
   127
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
   128
The following metacharacters and rules are respected.
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
   129
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
   130
=over
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
   131
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
   132
=item C<*> - match zero or more characters
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
   133
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
   134
C<a*> matches C<a>, C<aa>, C<aaaa> and many many more.
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
   135
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
   136
=item C<?> - match exactly one character
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
   137
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
   138
C<a?> matches C<aa>, but not C<a>, or C<aa>
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
   139
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
   140
=item Character sets/ranges
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
   141
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
   142
C<example.[ch]> matches C<example.c> and C<example.h>
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
   143
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
   144
C<demo.[a-c]> matches C<demo.a>, C<demo.b>, and C<demo.c>
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
   145
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
   146
=item alternation
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
   147
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
   148
C<example.{foo,bar,baz}> matches C<example.foo>, C<example.bar>, and
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
   149
C<example.baz>
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
   150
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
   151
=item leading . must be explictly matched
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
   152
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
   153
C<*.foo> does not match C<.bar.foo>.  For this you must either specify
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
   154
the leading . in the glob pattern (C<.*.foo>), or set
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
   155
C<$Text::Glob::strict_leading_dot> to a false value while compiling
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
   156
the regex.
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
   157
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
   158
=item C<*> and C<?> do not match /
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
   159
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
   160
C<*.foo> does not match C<bar/baz.foo>.  For this you must either
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
   161
explicitly match the / in the glob (C<*/*.foo>), or set
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
   162
C<$Text::Glob::strict_wildcard_slash> to a false value with compiling
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
   163
the regex.
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
   164
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
   165
=back
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
   166
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
   167
=head1 BUGS
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
   168
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
   169
The code uses qr// to produce compiled regexes, therefore this module
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
   170
requires perl version 5.005_03 or newer.
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
   171
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
   172
=head1 AUTHOR
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
   173
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
   174
Richard Clamp <richardc@unixbeard.net>
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
   175
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
   176
=head1 COPYRIGHT
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
   177
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
   178
Copyright (C) 2002 Richard Clamp.  All Rights Reserved.
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
   179
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
   180
This module is free software; you can redistribute it and/or modify it
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
   181
under the same terms as Perl itself.
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
   182
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
   183
=head1 SEE ALSO
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
   184
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
   185
L<File::Glob>, glob(3)
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
   186
3145852acc89 add releasing to new structure
jjkang
parents:
diff changeset
   187
=cut