NAME

File::Locate::Iterator -- read "locate" database with an iterator

SYNOPSIS

use File::Locate::Iterator;
my $it = File::Locate::Iterator->new;
while (defined (my $entry = $it->next)) {
  print $entry,"\n";
}

DESCRIPTION

File::Locate::Iterator reads a "locate" database file in iterator style. Each next() call on the iterator returns the next entry from the database.

Locate databases normally hold filenames as a way of finding files faster than churning through directories on the filesystem. Optional glob, suffix and regexp options on the iterator let you restrict the entries returned.

Only "LOCATE02" format files are supported per current versions of GNU locate, not the "slocate" format.

Iterators from this module are stand-alone, they don't need any of the various iterator frameworks. See Iterator::Locate and Iterator::Simple::Locate for inter-operating with those frameworks. The frameworks have the advantage of convenient ways to grep, map or manipulate the iterated sequence.

FUNCTIONS

$it = File::Locate::Iterator->new (key=>value,...)

Create and return a new locate database iterator object. The following optional key/value pairs are available,

database_file (default the system locate database)
database_fh

The file to read, either as filename or file handle. The default is the default_database_file below.

$it = File::Locate::Iterator->new
        (database_file => '/foo/bar.db');

A filehandle is read with the usual PerlIO, so it can come from various sources, but should generally be in binary mode.

suffix (string)
suffixes (arrayref of strings)
glob (string)
globs (arrayref of strings)
regexp (string or regexp object)
regexps (arrayref of strings or regexp objects)

Restrict the entries returned to those with given suffix(es) or matching the given glob(s) or regexp(s). For example,

# C code files on the system, .c and .h
$it = File::Locate::Iterator->new
        (suffixes => ['.c','.h']);

If multiple patterns or suffixes are given then matches of any are returned.

Globs are in the style of the locate program, which means fnmatch with no options (see File::FnMatch) and the pattern must match the full entry, except that a fixed string (none of "*", "?" or "[") can match anywhere.

$entry = $it->next

Return the next entry from the database, or no values at end of file. Recall that an empty return means undef in scalar context or no values in array context so you can loop with either

while (defined (my $filename = $it->next)) ...

or

while (my ($filename) = $it->next) ...

The return is a byte string since it's normally a filename (and as of Perl 5.10 filenames are handled as byte strings).

$filename = File::Locate::Iterator->default_database_file

Return the default database file used in new above. This is meant to be the same as the locate program uses and currently means /var/cache/locate/locatedb, but in the future it may be possible to check how findutils has been installed, or maybe even follow LOCATE_PATH.

FILES

/var/cache/locate/locatedb

Default locate database.

OTHER WAYS TO DO IT

File::Locate reads a locate database with callbacks. Whether you prefer callbacks or an iterator is a matter of style. Iterators let you write your own loop and can have multiple searches in progress simultaneously.

Iterators are good for cooperative coroutining like POE or Gtk where you must hold state in some sort of variable to be progressed by callbacks from the main loop. (Note that next() waits while reading from the database, so the database generally should be a plain file rather than a socket or something, so as not to hold up a main loop.)

When File::Locate is built with its XSUB code (requires Perl 5.10.0 or higher currently) the speed of an iterator is about the same as callbacks.

Currently each File::Locate::Iterator holds a separate open handle on the database, which means a file descriptor and PerlIO buffering per iterator. In the future hopefully some sharing among iterators can reduce resource requirements.

Sharing an open handle between iterators with each seeking to its desired position would be possible, but a seek drops buffered data and so would go slower than ever. There's some secret undocumented mmap code which should be both small and fast when an mmap is possible and isn't so huge as to eat up all your address space.

SEE ALSO

File::Locate, Iterator::Locate, Iterator::Simple::Locate, locate(1) and the GNU Findutils manual, File::FnMatch

HOME PAGE

http://user42.tuxfamily.org/file-locate-iterator/index.html

COPYRIGHT

Copyright 2009 Kevin Ryde

File-Locate-Iterator is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3, or (at your option) any later version.

File-Locate-Iterator is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details.

You should have received a copy of the GNU General Public License along with File-Locate-Iterator. If not, see http://www.gnu.org/licenses/