make sure all tests work in all combos, save the broken Directory deletion; POD doc...
Tara L Andrews [Fri, 14 Sep 2012 20:42:35 +0000 (22:42 +0200)]
27 files changed:
analysis/Makefile.PL
analysis/lib/Text/Tradition/Analysis.pm
analysis/t/03podcoverage.t
analysis/t/analysis.t
base/lib/Text/Tradition.pm
base/lib/Text/Tradition/Collation.pm
base/lib/Text/Tradition/Parser/Self.pm
base/t/03podcoverage.t
base/t/text_tradition_collation.t
morphology/Makefile.PL
morphology/lib/Text/Tradition/Collation/Reading/Lexeme.pm
morphology/lib/Text/Tradition/Collation/Reading/WordForm.pm
morphology/lib/Text/Tradition/Language.pm
morphology/lib/Text/Tradition/Language/Armenian.pm
morphology/lib/Text/Tradition/Language/Base.pm
morphology/lib/Text/Tradition/Language/English.pm
morphology/lib/Text/Tradition/Language/French.pm
morphology/lib/Text/Tradition/Language/Greek.pm
morphology/lib/Text/Tradition/Language/Latin.pm
morphology/lib/Text/Tradition/Language/Perseus.pm
morphology/lib/Text/Tradition/Morphology.pm
morphology/t/03podcoverage.t
persistence/Makefile.PL
persistence/lib/Text/Tradition/Directory.pm
persistence/lib/Text/Tradition/Ownership.pm [new file with mode: 0644]
persistence/t/03podcoverage.t
persistence/t/userrestore.t

index 62d8e49..41f8840 100644 (file)
@@ -18,9 +18,9 @@ requires( 'Moose' );
 requires( 'Moose::Role' );
 requires( 'Set::Scalar' );
 requires( 'Text::Tradition' );
-requires( 'Text::Tradition::Directory' );
 requires( 'Text::Tradition::Error' );
 requires( 'TryCatch' );
 
 build_requires( 'Test::More::UTF8' );
+build_requires( 'Text::Tradition::Directory' );
 &WriteAll;
index f245b94..7777f86 100644 (file)
@@ -10,7 +10,6 @@ use JSON qw/ to_json decode_json /;
 use LWP::UserAgent;
 use Set::Scalar;
 use Text::Tradition::Analysis::Result;
-use Text::Tradition::Directory;
 use Text::Tradition::Stemma;
 use TryCatch;
 
@@ -26,6 +25,30 @@ my $unsolved_problems = {};
 
 Text::Tradition::Analysis - functions for stemma analysis of a tradition
 
+=head1 DESCRIPTION
+
+Text::Tradition is a library for representation and analysis of collated
+texts, particularly medieval ones.  Where the Collation is the central
+feature of a Tradition, it may also have one or more stemmata associated
+with it, and these stemmata may be analyzed. This package provides the
+following modules:
+
+=over 4
+
+=item * L<Text::Tradition::HasStemma> - a role that will be composed into
+Text::Tradition objects, providing the ability for Text::Tradition::Stemma
+objects to be associated with them.
+
+=item * L<Text::Tradition::Stemma> - an object class that represents stemma
+hypotheses, both rooted (with a single archetype) and unrooted (e.g.
+phylogenetic trees).
+
+=item * Text::Tradition::Analysis (this package). Provides functions for
+the analysis of a given stemma against the collation within a given
+Tradition.
+
+=back
+
 =head1 SYNOPSIS
 
   use Text::Tradition;
@@ -37,25 +60,7 @@ Text::Tradition::Analysis - functions for stemma analysis of a tradition
   $t->add_stemma( 'dotfile' => $stemmafile );
 
   my $variant_data = run_analysis( $tradition );
-  # Recalculate rank $n treating all orthographic variants as equivalent
-  my $reanalyze = analyze_variant_location( $tradition, $n, 0, 'orthographic' );
     
-=head1 DESCRIPTION
-
-Text::Tradition is a library for representation and analysis of collated
-texts, particularly medieval ones.  Where the Collation is the central feature of
-a Tradition, it may also have one or more temmata associated with it, and these stemmata may be analyzed. This package provides the following modules:
-
-=over 4
-
-=item * L<Text::Tradition::HasStemma> - a role that can be composed into Text::Tradition objects, providing the ability for Text::Tradition::Stemma objects to be associated with them.
-
-=item * L<Text::Tradition::Stemma> - an object class that represents stemma hypotheses, both rooted (with a single archetype) and unrooted (e.g. phylogenetic trees).
-
-=item * Text::Tradition::Analysis (this package). Provides functions for the analysis of a given stemma against the collation within a given Tradition.
-
-=back
-
 =head1 SUBROUTINES
 
 =head2 run_analysis( $tradition, %opts )
@@ -171,6 +176,11 @@ sub run_analysis {
        if( exists $opts{'calcdir'} ) {
                $dir = delete $opts{'calcdir'}
        } elsif ( exists $opts{'calcdsn'} ) {
+               eval { require Text::Tradition::Directory };
+               if( $@ ) {
+                       throw( "Could not instantiate a directory for " . $opts{'calcdsn'}
+                               . ": $@" );
+               }
                $dir = Text::Tradition::Directory->new( dsn => $opts{'calcdsn'} );
        }
 
index d58a539..2d85544 100644 (file)
@@ -7,11 +7,8 @@ eval "use Test::Pod::Coverage 1.04";
 plan skip_all => 'Test::Pod::Coverage 1.04 required' if $@;
 plan skip_all => 'set TEST_POD to enable this test' unless $ENV{TEST_POD};
 
-my @exclude = qw/ Store Collation::Data TypeMap::Entry /;
-
 my %mods;
 map { $mods{$_} = 1 } all_modules();
-map { delete $mods{'Text::Tradition::'.$_} } @exclude;
 if( -e 'MANIFEST.SKIP' ) {
        open( SKIP, 'MANIFEST.SKIP' ) or die "Could not open skip file";
        while(<SKIP>) {
index bc5661f..cdb3b2a 100755 (executable)
@@ -18,8 +18,6 @@ my $tradition = Text::Tradition->new(
 $tradition->add_stemma( 'dotfile' => 't/data/besoin.dot' );
 
 # Run the analysis of the tradition
-## TODO Make proper test db
-my $calcdsn = 'dbi:SQLite:dbname=t/data/analysis.db';
 
 my %expected = (
     2 => 'type1',
index e85f366..769688f 100644 (file)
@@ -7,7 +7,6 @@ use Moose::Util qw/ does_role apply_all_roles /;
 use Text::Tradition::Collation;
 use Text::Tradition::Error;
 use Text::Tradition::Witness;
-use Text::Tradition::User;
 use TryCatch;
 
 use vars qw( $VERSION );
@@ -20,6 +19,7 @@ eval { with 'Text::Tradition::HasStemma'; };
 #      warn "Text::Tradition::Analysis not found. Disabling stemma analysis functionality";
 # };
 eval { with 'Text::Tradition::Language'; };
+eval { with 'Text::Tradition::Ownership'; };
 
 has 'collation' => (
     is => 'ro',
@@ -53,22 +53,6 @@ has '_initialized' => (
        writer => '_init_done',
        ); 
 
-has 'user' => (
-    is => 'rw',
-    isa => 'Text::Tradition::User',
-    required => 0,
-    predicate => 'has_user',
-    clearer => 'clear_user',
-    weak_ref => 1
-    );
-
-has 'public' => (
-    is => 'rw',
-    isa => 'Bool',
-    required => 0,
-    default => sub { 0; },
-    );
-
 # Create the witness before trying to add it
 around 'add_witness' => sub {
     my $orig = shift;
index 7c7335f..10426aa 100644 (file)
@@ -243,7 +243,8 @@ sub add_reading {
                        # If we are initializing an empty collation, don't assume that we
                        # have set a tradition.
                        delete $args{'init'};
-               } elsif( $self->tradition->can('language') && !exists $args{'language'} ) {
+               } elsif( $self->tradition->can('language') && $self->tradition->has_language
+                       && !exists $args{'language'} ) {
                        $args{'language'} = $self->tradition->language;
                }
                $reading = Text::Tradition::Collation::Reading->new( 
@@ -919,16 +920,6 @@ SKIP: {
        like( $graphml, qr/digraph/, "Digraph declaration exists in GraphML" );
 }
 
-# Now add a user, write to GraphML, and look at the output.
-unlike( $graphml, qr/testuser/, "Test user name does not exist in GraphML yet" );
-my $testuser = Text::Tradition::User->new( 
-       id => 'testuser', password => 'testpass' );
-is( ref( $testuser ), 'Text::Tradition::User', "Created test user object" );
-$testuser->add_tradition( $tradition );
-is( $tradition->user->id, $testuser->id, "Tradition assigned to test user" );
-$graphml = $c->as_graphml;
-like( $graphml, qr/testuser/, "Test user name now exists in GraphML" );
-
 =end testing
 
 =cut
@@ -1006,9 +997,11 @@ sub as_graphml {
                };
        }
        
-    $graph_attributes{'user'} = sub { 
-       $self->tradition->user ? $self->tradition->user->id : undef 
-    };
+       if( $tmeta->has_method('user') ) {
+               $graph_attributes{'user'} = sub { 
+                       $self->tradition->user ? $self->tradition->user->id : undef 
+               };
+       }
        
     foreach my $datum ( sort keys %graph_attributes ) {
        $graph_data_keys{$datum} = 'dg'.$gdi++;
index 55ec769..b9af342 100644 (file)
@@ -179,8 +179,6 @@ sub parse {
     $tradition->name( $graph_data->{'name'} );
 
     my $use_version;
-    my $tmeta = $tradition->meta;
-    my $cmeta = $collation->meta;
     foreach my $gkey ( keys %{$graph_data->{'global'}} ) {
                my $val = $graph_data->{'global'}->{$gkey};
                if( $gkey eq 'version' ) {
@@ -195,12 +193,6 @@ sub parse {
                        } else {
                                warn "Analysis module not installed; DROPPING stemmata";
                        }
-               } elsif( $gkey eq 'language' ) {
-                       if( $tradition->can('language') ) {
-                               $tradition->language( $val );
-                       } else {
-                               warn "Morphology module not installed; DROPPING language";
-                       }
                } elsif( $gkey eq 'user' ) {
                        # Assign the tradition to the user if we can
                        if( exists $opts->{'userstore'} ) {
@@ -214,10 +206,12 @@ sub parse {
                        } else {
                                warn( "DROPPING user assignment without a specified userstore" );
                        }
-               } elsif( $tmeta->has_attribute( $gkey ) ) {
+               } elsif( $tradition->can( $gkey ) ) {
                        $tradition->$gkey( $val );
-               } else {
+               } elsif( $collation->can( $gkey ) ) {
                        $collation->$gkey( $val );
+               } else {
+                       warn( "DROPPING unsupported attribute $gkey" );
                }
        }
                
index d58a539..c458f7e 100644 (file)
@@ -7,7 +7,7 @@ eval "use Test::Pod::Coverage 1.04";
 plan skip_all => 'Test::Pod::Coverage 1.04 required' if $@;
 plan skip_all => 'set TEST_POD to enable this test' unless $ENV{TEST_POD};
 
-my @exclude = qw/ Store Collation::Data TypeMap::Entry /;
+my @exclude = qw/ Collation::Data /;
 
 my %mods;
 map { $mods{$_} = 1 } all_modules();
index a83e11e..9e998c6 100644 (file)
@@ -95,16 +95,6 @@ SKIP: {
        $graphml = $c->as_graphml;
        like( $graphml, qr/digraph/, "Digraph declaration exists in GraphML" );
 }
-
-# Now add a user, write to GraphML, and look at the output.
-unlike( $graphml, qr/testuser/, "Test user name does not exist in GraphML yet" );
-my $testuser = Text::Tradition::User->new( 
-       id => 'testuser', password => 'testpass' );
-is( ref( $testuser ), 'Text::Tradition::User', "Created test user object" );
-$testuser->add_tradition( $tradition );
-is( $tradition->user->id, $testuser->id, "Tradition assigned to test user" );
-$graphml = $c->as_graphml;
-like( $graphml, qr/testuser/, "Test user name now exists in GraphML" );
 }
 
 
index 21de75b..a326c7a 100644 (file)
@@ -7,7 +7,9 @@ perl_version( '5.012' );
 all_from( 'lib/Text/Tradition/Morphology.pm' );
 requires( 'IPC::Run' );
 requires( 'JSON' );
+requires( 'Lingua::Features' => '0.3.2' );
 requires( 'Lingua::Features::Structure' );
+requires( 'Lingua::TagSet' => '0.3.3' );
 requires( 'Lingua::TagSet::Multext' );
 requires( 'Lingua::TagSet::TreeTagger::French' );
 requires( 'Lingua::TagSet::TreeTagger::English' );
index fa564ee..a8caed3 100644 (file)
@@ -203,12 +203,3 @@ __PACKAGE__->meta->make_immutable;
 
 1;
 
-=head1 LICENSE
-
-This package is free software and is provided "as is" without express
-or implied warranty.  You can redistribute it and/or modify it under
-the same terms as Perl itself.
-
-=head1 AUTHOR
-
-Tara L Andrews E<lt>aurum@cpan.orgE<gt>
index 968f205..1a91367 100644 (file)
@@ -126,12 +126,3 @@ __PACKAGE__->meta->make_immutable;
 
 1;
 
-=head1 LICENSE
-
-This package is free software and is provided "as is" without express
-or implied warranty.  You can redistribute it and/or modify it under
-the same terms as Perl itself.
-
-=head1 AUTHOR
-
-Tara L Andrews E<lt>aurum@cpan.orgE<gt>
index 01b3ba6..3a78744 100644 (file)
@@ -10,8 +10,9 @@ requires 'throw';
 =head1 NAME
 
 Text::Tradition::Language - add-on role to enable language awareness and 
-morphology functions to a Text::Tradition object.  See also 
-L<Text::Tradition::Morphology> for individual reading morphologies.
+morphology functions to a Text::Tradition object.  Please see
+L<Text::Tradition::Morphology> for more information on the morphology 
+add-on distribution.
 
 =head1 METHODS
 
@@ -59,12 +60,3 @@ sub lemmatize {
 
 1;
 
-=head1 LICENSE
-
-This package is free software and is provided "as is" without express
-or implied warranty.  You can redistribute it and/or modify it under
-the same terms as Perl itself.
-
-=head1 AUTHOR
-
-Tara L Andrews E<lt>aurum@cpan.orgE<gt>
index f6b8aa9..3030f0f 100644 (file)
@@ -72,12 +72,3 @@ sub reading_lookup {
 
 1;
 
-=head1 LICENSE
-
-This package is free software and is provided "as is" without express
-or implied warranty.  You can redistribute it and/or modify it under
-the same terms as Perl itself.
-
-=head1 AUTHOR
-
-Tara L Andrews E<lt>aurum@cpan.orgE<gt>
index f0fe304..fd56c04 100644 (file)
@@ -293,12 +293,3 @@ sub _by_structid {
 
 =back
 
-=head1 LICENSE
-
-This package is free software and is provided "as is" without express
-or implied warranty.  You can redistribute it and/or modify it under
-the same terms as Perl itself.
-
-=head1 AUTHOR
-
-Tara L Andrews E<lt>aurum@cpan.orgE<gt>
index e1fee8d..4277d62 100644 (file)
@@ -99,12 +99,3 @@ sub _parse_wordform {
 
 =back
 
-=head1 LICENSE
-
-This package is free software and is provided "as is" without express
-or implied warranty.  You can redistribute it and/or modify it under
-the same terms as Perl itself.
-
-=head1 AUTHOR
-
-Tara L Andrews E<lt>aurum@cpan.orgE<gt>
index 9dbfd01..13ad869 100644 (file)
@@ -183,12 +183,3 @@ sub _parse_wordform {
 
 =back
 
-=head1 LICENSE
-
-This package is free software and is provided "as is" without express
-or implied warranty.  You can redistribute it and/or modify it under
-the same terms as Perl itself.
-
-=head1 AUTHOR
-
-Tara L Andrews E<lt>aurum@cpan.orgE<gt>
index d857417..8106ec6 100644 (file)
@@ -72,12 +72,3 @@ sub reading_lookup {
 
 1;
 
-=head1 LICENSE
-
-This package is free software and is provided "as is" without express
-or implied warranty.  You can redistribute it and/or modify it under
-the same terms as Perl itself.
-
-=head1 AUTHOR
-
-Tara L Andrews E<lt>aurum@cpan.orgE<gt>
index 9ba62da..ad36208 100644 (file)
@@ -72,12 +72,3 @@ sub reading_lookup {
 
 1;
 
-=head1 LICENSE
-
-This package is free software and is provided "as is" without express
-or implied warranty.  You can redistribute it and/or modify it under
-the same terms as Perl itself.
-
-=head1 AUTHOR
-
-Tara L Andrews E<lt>aurum@cpan.orgE<gt>
index 4939a2c..9818d00 100644 (file)
@@ -135,12 +135,8 @@ sub _wordform_from_row {
        
 1;
 
-=head1 LICENSE
+=head1 ACKNOWLEDGMENTS
 
-This package is free software and is provided "as is" without express
-or implied warranty.  You can redistribute it and/or modify it under
-the same terms as Perl itself.
-
-=head1 AUTHOR
-
-Tara L Andrews E<lt>aurum@cpan.orgE<gt>
+The Perseus model and its dependents (currently Latin and Greek) draws its
+data from the ARTFL project at the University of Chicago. The module author
+wishes to thank Helma Dik in particular for her kind assistance.
\ No newline at end of file
index bedba04..a0581f2 100644 (file)
@@ -12,8 +12,18 @@ $VERSION = "0.1";
 
 =head1 NAME
 
-Text::Tradition::Morphology - add-on to associate lemma and part-of-speech 
-information to Text::Tradition::Collation::Reading objects
+Text::Tradition::Morphology - morphology plugin for Text::Tradition
+
+=head1 DESCRIPTION
+
+The Text::Tradition::Morphology package enables lemma and part-of-speech
+information for traditions and their Reading objects. This distribution
+includes the L<Text::Tradition::Language> role for Traditions, the
+L<Text::Tradition::Morphology> role (this package) for Readings, and a set
+of Language::* modules for language-specific lemmatization.
+
+See L<Text::Tradition::Collation::Reading::Lexeme> for more about the 
+morphology object structure.
 
 =cut
 
@@ -69,7 +79,7 @@ around 'normal_form' => sub {
        }
 };
 
-=head1 METHODS
+=head1 READING METHODS
 
 Methods for the morphological information (if any) attached to readings.
 A reading may be made up of multiple lexemes; the concatenated lexeme
@@ -98,7 +108,7 @@ Adds the Lexeme in $lexobj to the list of lexemes.
 
 If the language of the reading is set, this method will use the appropriate
 Language model to determine the lexemes that belong to this reading.  See
-L<Text::Tradition::lemmatize> if you wish to lemmatize an entire tradition.
+L<Text::Tradition::Language::lemmatize> if you wish to lemmatize an entire tradition.
 
 =cut
 
index d58a539..2d85544 100644 (file)
@@ -7,11 +7,8 @@ eval "use Test::Pod::Coverage 1.04";
 plan skip_all => 'Test::Pod::Coverage 1.04 required' if $@;
 plan skip_all => 'set TEST_POD to enable this test' unless $ENV{TEST_POD};
 
-my @exclude = qw/ Store Collation::Data TypeMap::Entry /;
-
 my %mods;
 map { $mods{$_} = 1 } all_modules();
-map { delete $mods{'Text::Tradition::'.$_} } @exclude;
 if( -e 'MANIFEST.SKIP' ) {
        open( SKIP, 'MANIFEST.SKIP' ) or die "Could not open skip file";
        while(<SKIP>) {
index e5dadc7..66e6fb1 100644 (file)
@@ -15,6 +15,7 @@ requires( 'KiokuDB::TypeMap::Entry::Naive' );
 requires( 'KiokuX::Model' );
 requires( 'KiokuX::User::Util' );
 requires( 'Moose' );
+requires( 'Moose::Role' );
 requires( 'Safe::Isa' );
 requires( 'TryCatch' );
 requires( 'YAML::XS' );
index d99a888..61e88d7 100644 (file)
@@ -19,9 +19,13 @@ use Text::Tradition::TypeMap::Entry;
 
 extends 'KiokuX::Model';
 
+use vars qw/ $VERSION /;
+$VERSION = "1.0";
+
 =head1 NAME
 
-Text::Tradition::Directory - a KiokuDB interface for storing and retrieving traditions
+Text::Tradition::Directory - a KiokuDB interface for storing and retrieving 
+traditions and their owners
 
 =head1 SYNOPSIS
 
@@ -56,7 +60,16 @@ Text::Tradition::Directory - a KiokuDB interface for storing and retrieving trad
     
 =head1 DESCRIPTION
 
-Text::Tradition::Directory is an interface for storing and retrieving text traditions and all their data, including an associated stemma hypothesis.  It is an instantiation of a KiokuDB::Model, storing traditions and associated stemmas by UUID.
+Text::Tradition::Directory is an interface for storing and retrieving text
+traditions and all their data, including an associated stemma hypothesis
+and a user who has ownership rights to the tradition data. It is an
+instantiation of a KiokuDB::Model, storing traditions and associated
+stemmas by UUID.
+
+The Text::Tradition::Directory package also includes the
+L<Text::Tradition::User> class for user objects, and the
+L<Text::Tradition::Ownership> role which extends the Text::Tradition class
+to handle user ownership.
 
 =head1 ATTRIBUTES
 
@@ -654,6 +667,9 @@ This package is free software and is provided "as is" without express
 or implied warranty.  You can redistribute it and/or modify it under
 the same terms as Perl itself.
 
-=head1 AUTHOR
+=head1 AUTHORS
+
+Tara L Andrews E<lt>aurum@cpan.orgE<gt> (initial release)
+
+Shadowcat Systems L<http://www.scsys.co.uk/> (user functionality; making it all work)
 
-Tara L Andrews E<lt>aurum@cpan.orgE<gt>
diff --git a/persistence/lib/Text/Tradition/Ownership.pm b/persistence/lib/Text/Tradition/Ownership.pm
new file mode 100644 (file)
index 0000000..dd64e2c
--- /dev/null
@@ -0,0 +1,46 @@
+package Text::Tradition::Ownership;
+
+use strict;
+use warnings;
+use Moose::Role;
+use Text::Tradition::User;
+
+requires 'throw';
+
+=head1 NAME
+
+Text::Tradition::Ownership - add-on role to enable Text::Tradition objects
+to have users who own them.
+
+=head1 METHODS
+
+=head2 user
+
+Accessor for the owner of the tradition.
+
+=head2 public
+
+Whether this tradition should be accessible (readonly) to anyone who is not
+the owner.
+
+=cut
+
+has 'user' => (
+    is => 'rw',
+    isa => 'Text::Tradition::User',
+    required => 0,
+    predicate => 'has_user',
+    clearer => 'clear_user',
+    weak_ref => 1
+    );
+
+has 'public' => (
+    is => 'rw',
+    isa => 'Bool',
+    required => 0,
+    default => sub { 0; },
+    );
+
+    
+1;
+
index d58a539..ed6ec8d 100644 (file)
@@ -7,7 +7,7 @@ eval "use Test::Pod::Coverage 1.04";
 plan skip_all => 'Test::Pod::Coverage 1.04 required' if $@;
 plan skip_all => 'set TEST_POD to enable this test' unless $ENV{TEST_POD};
 
-my @exclude = qw/ Store Collation::Data TypeMap::Entry /;
+my @exclude = qw/ Store TypeMap::Entry /;
 
 my %mods;
 map { $mods{$_} = 1 } all_modules();
index 3c734b1..ef5fc87 100644 (file)
@@ -11,6 +11,9 @@ use Text::Tradition::Directory;
 
 my $newt = Text::Tradition->new( 'input' => 'Self', 
        'file' => 't/data/florilegium_graphml.xml' );
+       
+my $graphml = $newt->collation->as_graphml;
+unlike( $graphml, qr/testuser/, "Test user name does not exist in GraphML yet" );
 
 my $fh = File::Temp->new();
 my $file = $fh->filename;