Skip to content

Commit

Permalink
Import of RHOELZ/Mac-FSEvents-0.08 from CPAN.
Browse files Browse the repository at this point in the history
gitpan-cpan-distribution: Mac-FSEvents
gitpan-cpan-version:      0.08
gitpan-cpan-path:         RHOELZ/Mac-FSEvents-0.08.tar.gz
gitpan-cpan-author:       RHOELZ
gitpan-cpan-maturity:     released
  • Loading branch information
hoelzro authored and Gitpan committed Oct 26, 2014
1 parent 10292bb commit ed72d07
Show file tree
Hide file tree
Showing 12 changed files with 461 additions and 5 deletions.
3 changes: 3 additions & 0 deletions Changes
@@ -1,5 +1,8 @@
Revision history for Perl extension Mac::FSEvents.

0.08 2012-05-28 14:00:00
- fix broken MANIFEST

0.07 2012-05-21 19:15:00
- Allow users to specify creation flags for FSEvents.
- Fix the compilation option detection process.
Expand Down
6 changes: 6 additions & 0 deletions MANIFEST
Expand Up @@ -3,6 +3,7 @@ FSEvents.xs
hints/darwin.pl
lib/Mac/FSEvents.pm
lib/Mac/FSEvents/Event.pm
MacVersion.pm
Makefile.PL
MANIFEST
ppport.h
Expand All @@ -13,6 +14,11 @@ t/03podcoverage.t
t/04critic.rc
t/04critic.t
t/05event.t
t/06flags.t
t/07noflags.t
t/08leftover-events.t
t/09subprocess-events.t
t/10receive-all-changes.t
typemap
META.yml Module meta-data (added by MakeMaker)
META.json Module JSON meta-data (added by MakeMaker)
5 changes: 3 additions & 2 deletions META.json
@@ -1,7 +1,8 @@
{
"abstract" : "Monitor a directory structure for changes",
"author" : [
"Andy Grundman <andy@hybridized.org>"
"Andy Grundman <andy@hybridized.org>",
"Rob Hoelz `<rob@hoelz.ro>"
],
"dynamic_config" : 1,
"generated_by" : "ExtUtils::MakeMaker version 6.6302, CPAN::Meta::Converter version 2.120630",
Expand Down Expand Up @@ -37,5 +38,5 @@
}
},
"release_status" : "stable",
"version" : "0.07"
"version" : "0.08"
}
3 changes: 2 additions & 1 deletion META.yml
Expand Up @@ -2,6 +2,7 @@
abstract: 'Monitor a directory structure for changes'
author:
- 'Andy Grundman <andy@hybridized.org>'
- 'Rob Hoelz `<rob@hoelz.ro>'
build_requires:
ExtUtils::MakeMaker: 0
configure_requires:
Expand All @@ -19,4 +20,4 @@ no_index:
- inc
requires:
File::Slurp: 0
version: 0.07
version: 0.08
30 changes: 30 additions & 0 deletions MacVersion.pm
@@ -0,0 +1,30 @@
package
MacVersion;

use strict;
use warnings;
use base 'Exporter';

our @EXPORT = qw(osx_version);

sub osx_version {
my $os_version = qx(system_profiler SPSoftwareDataType);
if($os_version =~ /System Version: Mac OS X (?:Server )?(10\.\d+)/) {
return $1;
} else {
$os_version =~ s/^/> /gm;

die <<"END_DIE";
Could not parse version string!
Please file a bug report on CPAN, and include the following
in the description:
$os_version
END_DIE

exit 1;
}

}

1;
2 changes: 1 addition & 1 deletion Makefile.PL
Expand Up @@ -10,7 +10,7 @@ WriteMakefile(
VERSION_FROM => 'lib/Mac/FSEvents.pm',
PREREQ_PM => {},
ABSTRACT_FROM => 'lib/Mac/FSEvents.pm',
AUTHOR => 'Andy Grundman <andy@hybridized.org>',
AUTHOR => [ 'Andy Grundman <andy@hybridized.org>', 'Rob Hoelz `<rob@hoelz.ro>' ],
LIBS => [''],
LDDLFLAGS => $Config{lddlflags} . ' -framework CoreServices -framework CoreFoundation',
DEFINE => '',
Expand Down
2 changes: 1 addition & 1 deletion lib/Mac/FSEvents.pm
Expand Up @@ -6,7 +6,7 @@ use base 'Exporter';

use Mac::FSEvents::Event;

our $VERSION = '0.07';
our $VERSION = '0.08';

our @EXPORT_OK = qw(NONE WATCH_ROOT);
our %EXPORT_TAGS = ( flags => \@EXPORT_OK );
Expand Down
214 changes: 214 additions & 0 deletions t/06flags.t
@@ -0,0 +1,214 @@
use strict;
use warnings;
use autodie;

use Carp qw(croak);
use Cwd qw(getcwd);
use FindBin;
use File::Path qw(make_path rmtree);
use File::Spec;
use File::Temp;
use IO::Select;
use Mac::FSEvents qw(:flags);
use Time::HiRes qw(usleep);

use Test::More tests => 5;

my %capable_of;

BEGIN {
foreach my $constant ( qw{IGNORE_SELF FILE_EVENTS} ) {
if(__PACKAGE__->can($constant)) {
$capable_of{$constant} = 1;
} else {
no strict 'refs';

*$constant = sub {
return 0;
};
}
}
}

my $TEST_LATENCY = 0.5;
my $TIMEOUT = 3;

my $tmpdir = "$FindBin::Bin/tmp";

sub touch_file {
my ( $filename ) = @_;

my $fh;
open $fh, '>', $filename or die $!;
close $fh;

return;
}

sub reset_fs {
rmtree $tmpdir if -d $tmpdir;

mkdir $tmpdir;
}

sub with_wd (&$) {
my ( $callback, $dir ) = @_;

my $wd = getcwd();

local $Test::Builder::Level = $Test::Builder::Level + 1;

my $ok = eval {
chdir $dir or croak $!;

$callback->();
1;
};
my $error = $@;
chdir $wd;
die $error unless $ok;

return;
}

sub dissect_event {
my ( $event ) = @_;

return {
path => $event->path,
};
}

sub fetch_events {
my ( $fs, $fh ) = @_;

my @events;

my $sel = IO::Select->new($fh);

while( $sel->can_read($TIMEOUT) ) {
foreach my $event ( $fs->read_events ) {
push @events, $event;
}
}

return @events;
}

sub normalize_event {
my ( $event ) = @_;

my $path;

if(ref($event) eq 'Mac::FSEvents::Event') {
$path = $event->path;
} else {
$path = $event->{'path'};
}
$event = {};

$event->{'path'} = File::Spec->canonpath($path);

return $event;
}

sub cmp_events {
my ( $lhs, $rhs ) = @_;

local $Test::Builder::Level = $Test::Builder::Level + 1;

foreach my $event (@$lhs, @$rhs) {
$event = normalize_event($event);
}

return is_deeply($lhs, $rhs);
};

sub test_flags {
my ( $flags, $create_files, $expected_events ) = @_;

reset_fs();

local $Test::Builder::Level = $Test::Builder::Level + 1;

sleep 1; # wait for reset_fs triggered events to pass

my $fs = Mac::FSEvents->new({
path => $tmpdir,
latency => $TEST_LATENCY,
flags => $flags,
});

my $fh = $fs->watch;

with_wd {
$create_files->();
} $tmpdir;

my @events = map { normalize_event($_) } fetch_events($fs, $fh);

$fs->stop;

return cmp_events \@events, $expected_events;
}

sub test_watch_root {
reset_fs();

local $Test::Builder::Level = $Test::Builder::Level + 1;

with_wd {
make_path('foo/bar');

my $fs = Mac::FSEvents->new({
path => 'foo/bar',
latency => $TEST_LATENCY,
flags => WATCH_ROOT,
});

my $fh = $fs->watch;

usleep 100_000; # XXX wait a little for watcher to catch up;
# this is a bug that I'll fix!

rename 'foo/bar', 'foo/baz' or die $!;

my @events = fetch_events($fs, $fh);

is scalar(@events), 1;
ok $events[0]->root_changed;
} $tmpdir;
}

test_flags(NONE, sub {
touch_file 'foo.txt';
touch_file 'bar.txt';
}, [
{ path => $tmpdir }, # one event, because it's coalesced
]);

test_watch_root();

SKIP: {
skip q{Your platform doesn't support IGNORE_SELF}, 1 unless($capable_of{'IGNORE_SELF'});

test_flags(IGNORE_SELF, sub {
mkdir 'foo';

system 'touch foo/bar.txt';
}, [
{ path => "$tmpdir/foo" },
]);
}

SKIP: {
skip q{Your platform doesn't support FILE_EVENTS}, 1 unless $capable_of{'FILE_EVENTS'};

test_flags(FILE_EVENTS, sub {
touch_file 'foo.txt';
touch_file 'bar.txt';
}, [
{ path => "$tmpdir/foo.txt" },
{ path => "$tmpdir/bar.txt" },
]);
}
18 changes: 18 additions & 0 deletions t/07noflags.t
@@ -0,0 +1,18 @@
use strict;
use warnings;

use Mac::FSEvents;
use Test::More;

my @FLAGS = qw{
NONE
WATCH_ROOT
IGNORE_SELF
FILE_EVENTS
};

plan tests => scalar(@FLAGS);

foreach my $flag (@FLAGS) {
ok !__PACKAGE__->can($flag), 'flags should not be imported unless :flags is specified';
}
43 changes: 43 additions & 0 deletions t/08leftover-events.t
@@ -0,0 +1,43 @@
use strict;
use warnings;

use File::Temp;
use IO::Select;
use Mac::FSEvents;

use Test::More skip_all => 'This is a problem with FSEvents itself, it seems';

my $LATENCY = 0.5;
my $TIMEOUT = 1.0;

my $dir = File::Temp->newdir;

my $fs = Mac::FSEvents->new({
path => $dir->dirname,
latency => $LATENCY,
});

my $fh = $fs->watch;
my $sel = IO::Select->new($fh);

mkdir "$dir/foo";

my $has_events = $sel->can_read($TIMEOUT);
ok $has_events, q{we should have an event to process the first time around};

$fs->stop;

undef $fs;

rmdir "$dir/foo";

$fs = Mac::FSEvents->new({
path => $dir->dirname,
latency => $LATENCY,
});

$fh = $fs->watch;
$sel = IO::Select->new($fh);
$has_events = $sel->can_read($TIMEOUT);

ok !$has_events, q{a new watcher shouldn't receive old events};

0 comments on commit ed72d07

Please sign in to comment.