1 dnl PSPP - a program for statistical analysis.
2 dnl Copyright (C) 2017 Free Software Foundation, Inc.
4 dnl This program is free software: you can redistribute it and/or modify
5 dnl it under the terms of the GNU General Public License as published by
6 dnl the Free Software Foundation, either version 3 of the License, or
7 dnl (at your option) any later version.
9 dnl This program is distributed in the hope that it will be useful,
10 dnl but WITHOUT ANY WARRANTY; without even the implied warranty of
11 dnl MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12 dnl GNU General Public License for more details.
14 dnl You should have received a copy of the GNU General Public License
15 dnl along with this program. If not, see <http://www.gnu.org/licenses/>.
17 AT_BANNER([Perl module tests])
19 dnl This command can be used to run with the PSPP Perl module after it has been
20 dnl built (with "make") but before it has been installed. The -I options are
21 dnl equivalent to "use ExtUtils::testlib;" inside the Perl program, but it does
22 dnl not need to be run with the perl-module build directory as the current
23 dnl working directory.
25 dnl XXX "libtool --mode=execute" is probably better than setting
27 m4_define([RUN_PERL_MODULE],
28 [LD_LIBRARY_PATH=$abs_top_builddir/src/.libs \
29 LD_PRELOAD=/usr/lib/i386-linux-gnu/libasan.so.4 \
30 DYLD_LIBRARY_PATH=$abs_top_builddir/src/.libs \
31 $PERL -I$abs_top_builddir/perl-module/blib/arch \
32 -I$abs_top_builddir/perl-module/blib/lib])
34 AT_SETUP([Perl create system file])
35 AT_SKIP_IF([test "$WITH_PERL_MODULE" = no])
41 my $d = PSPP::Dict->new();
42 die "dictionary creation" if !ref $d;
43 die if $d->get_var_cnt () != 0;
45 $d->set_label ("My Dictionary");
46 $d->set_documents ("These Documents");
48 # Tests for variable creation
50 my $var0 = PSPP::Var->new ($d, "le");
51 die "trap illegal variable name" if ref $var0;
52 die if $d->get_var_cnt () != 0;
54 $var0 = PSPP::Var->new ($d, "legal");
55 die "accept legal variable name" if !ref $var0;
56 die if $d->get_var_cnt () != 1;
58 my $var1 = PSPP::Var->new ($d, "money",
59 (fmt=>PSPP::Fmt::DOLLAR,
60 width=>4, decimals=>2) );
61 die "cappet valid format" if !ref $var1;
62 die if $d->get_var_cnt () != 2;
64 $d->set_weight ($var1);
66 my $sysfile = PSPP::Sysfile->new ('testfile.sav', $d);
67 die "create sysfile object" if !ref $sysfile;
71 AT_CHECK([RUN_PERL_MODULE test.pl])
72 AT_DATA([dump-dict.sps],
73 [GET FILE='testfile.sav'.
79 AT_CHECK([pspp -O format=csv dump-dict.sps], [0], [dnl
87 Name,Position,Label,Measurement Level,Role,Width,Alignment,Print Format,Write Format,Missing Values
88 legal,1,,Scale,Input,8,Right,F9.2,F9.2,
89 money,2,,Scale,Input,8,Right,DOLLAR6.2,DOLLAR6.2,
91 dump-dict.sps:5: note: SHOW: WEIGHT is money.
95 AT_SETUP([Perl writing cases to system files])
96 AT_SKIP_IF([test "$WITH_PERL_MODULE" = no])
102 my $d = PSPP::Dict->new();
103 PSPP::Var->new ($d, "id",
111 PSPP::Var->new ($d, "name",
118 $d->set_documents ("This should not appear");
119 $d->clear_documents ();
120 $d->add_document ("This is a document line");
122 $d->set_label ("This is the file label");
124 # Check that we can write cases to system files.
125 my $sysfile = PSPP::Sysfile->new ("testfile.sav", $d);
126 my $res = $sysfile->append_case ( [34, "frederick"]);
127 die "append case" if !$res;
129 $res = $sysfile->append_case ( [34, "frederick", "extra"]);
130 die "append case with too many variables" if $res;
133 # Check that sysfiles are closed properly automaticallly in the destructor.
134 my $sysfile2 = PSPP::Sysfile->new ("testfile2.sav", $d);
135 $res = $sysfile2->append_case ( [21, "wheelbarrow"]);
136 die "append case 2" if !$res;
138 $res = $sysfile->append_case ( [34, "frederick", "extra"]);
139 die "append case with too many variables" if $res;
141 # Don't close. We want to test that the destructor does that.
143 AT_CHECK([RUN_PERL_MODULE test.pl])
144 AT_DATA([dump-dicts.sps],
145 [GET FILE='testfile.sav'.
151 GET FILE='testfile2.sav'.
157 AT_CHECK([pspp -O format=csv dump-dicts.sps], [0], [dnl
159 Name,Position,Label,Measurement Level,Role,Width,Alignment,Print Format,Write Format,Missing Values
160 id,1,,Scale,Input,8,Right,F2.0,F2.0,
161 name,2,,Nominal,Input,20,Left,A20,A20,
164 Label,This is the file label
167 This is a document line
174 Name,Position,Label,Measurement Level,Role,Width,Alignment,Print Format,Write Format,Missing Values
175 id,1,,Scale,Input,8,Right,F2.0,F2.0,
176 name,2,,Nominal,Input,20,Left,A20,A20,
179 Label,This is the file label
182 This is a document line
190 AT_SETUP([Perl write variable parameters])
191 AT_SKIP_IF([test "$WITH_PERL_MODULE" = no])
197 my $dict = PSPP::Dict->new();
198 die "dictionary creation" if !ref $dict;
200 my $int = PSPP::Var->new ($dict, "integer",
201 (width=>8, decimals=>0) );
203 $int->set_label ("My Integer");
205 $int->add_value_label (99, "Silly");
206 $int->clear_value_labels ();
207 $int->add_value_label (0, "Zero");
208 $int->add_value_label (1, "Unity");
209 $int->add_value_label (2, "Duality");
211 my $str = PSPP::Var->new ($dict, "string",
212 (fmt=>PSPP::Fmt::A, width=>8) );
215 $str->set_label ("My String");
216 $str->add_value_label ("xx", "foo");
217 $str->add_value_label ("yy", "bar");
219 $str->set_missing_values ("this", "that");
221 my $longstr = PSPP::Var->new ($dict, "longstring",
222 (fmt=>PSPP::Fmt::A, width=>9) );
225 $longstr->set_label ("My Long String");
226 my $re = $longstr->add_value_label ("xxx", "xfoo");
228 $int->set_missing_values (9, 99);
230 my $sysfile = PSPP::Sysfile->new ("testfile.sav", $dict);
235 AT_CHECK([RUN_PERL_MODULE test.pl], [0], [], [stderr])
237 AT_DATA([dump-dict.sps],
238 [GET FILE='testfile.sav'.
241 AT_CHECK([pspp -O format=csv dump-dict.sps], [0], [dnl
243 Name,Position,Label,Measurement Level,Role,Width,Alignment,Print Format,Write Format,Missing Values
244 integer,1,My Integer,Scale,Input,8,Right,F8.0,F8.0,9; 99
245 string,2,My String,Nominal,Input,8,Left,A8,A8,"""this ""; ""that """
246 longstring,3,My Long String,Nominal,Input,9,Left,A9,A9,
249 Variable Value,,Label
255 My Long String,xxx,xfoo
259 AT_SETUP([Perl dictionary survives system file])
260 AT_SKIP_IF([test "$WITH_PERL_MODULE" = no])
269 my $d = PSPP::Dict->new();
271 PSPP::Var->new ($d, "id",
279 $sysfile = PSPP::Sysfile->new ("testfile.sav", $d);
282 my $res = $sysfile->append_case ([3]);
283 print "Dictionary survives sysfile\n" if $res;
285 AT_CHECK([RUN_PERL_MODULE test.pl], [0],
286 [Dictionary survives sysfile
290 m4_define([PERL_GENERATE_SYSFILE],
291 [AT_DATA([sample.sps],
292 [[data list notable list /string (a8) longstring (a12) numeric (f10) date (date11) dollar (dollar8.2) datetime (datetime17)
294 1111 One 1 1/1/1 1 1/1/1+01:01
295 2222 Two 2 2/2/2 2 2/2/2+02:02
296 3333 Three 3 3/3/3 3 3/3/3+03:03
298 5555 Five 5 5/5/5 5 5/5/5+05:05
302 variable labels string 'A Short String Variable'
303 /longstring 'A Long String Variable'
304 /numeric 'A Numeric Variable'
305 /date 'A Date Variable'
306 /dollar 'A Dollar Variable'
307 /datetime 'A Datetime Variable'.
310 missing values numeric (9, 5, 999).
312 missing values string ("3333").
315 /string '1111' 'ones' '2222' 'twos' '3333' 'threes'
316 /numeric 1 'Unity' 2 'Duality' 3 'Thripality'.
320 attribute=colour[1]('blue') colour[2]('pink') colour[3]('violet')
321 attribute=size('large') nationality('foreign').
324 save outfile='sample.sav'.
326 AT_CHECK([pspp -O format=csv sample.sps])])
328 AT_SETUP([Perl read system file])
329 AT_SKIP_IF([test "$WITH_PERL_MODULE" = no])
330 PERL_GENERATE_SYSFILE
336 my $sf = PSPP::Reader->open ("sample.sav");
338 my $dict = $sf->get_dict ();
340 for (my $v = 0 ; $v < $dict->get_var_cnt() ; $v++)
342 my $var = $dict->get_var ($v);
343 my $name = $var->get_name ();
344 my $label = $var->get_label ();
346 print "Variable $v is \"$name\", label is \"$label\"\n";
348 my $vl = $var->get_value_labels ();
350 print "Value Labels:\n";
351 print "$_ => $vl->{$_}\n" for sort (keys %$vl);
354 while (my @c = $sf->get_next_case () )
356 for (my $v = 0; $v < $dict->get_var_cnt(); $v++)
358 print "val$v: \"$c[$v]\"\n";
363 AT_CHECK([RUN_PERL_MODULE test.pl], [0],
364 [Variable 0 is "string", label is "A Short String Variable"
369 Variable 1 is "longstring", label is "A Long String Variable"
371 Variable 2 is "numeric", label is "A Numeric Variable"
376 Variable 3 is "date", label is "A Date Variable"
378 Variable 4 is "dollar", label is "A Dollar Variable"
380 Variable 5 is "datetime", label is "A Datetime Variable"
420 AT_SETUP([Perl copying system files])
421 AT_SKIP_IF([test "$WITH_PERL_MODULE" = no])
422 PERL_GENERATE_SYSFILE
428 my $input = PSPP::Reader->open ("sample.sav");
430 my $dict = $input->get_dict ();
432 my $output = PSPP::Sysfile->new ("copy.sav", $dict);
434 while (my (@c) = $input->get_next_case () )
436 $output->append_case (\@c);
441 AT_CHECK([RUN_PERL_MODULE test.pl])
442 AT_DATA([dump-dicts.sps],
443 [GET FILE='sample.sav'.
453 AT_CHECK([pspp -O format=csv dump-dicts.sps], [0],
455 Name,Position,Label,Measurement Level,Role,Width,Alignment,Print Format,Write Format,Missing Values
456 string,1,A Short String Variable,Nominal,Input,8,Left,A8,A8,"""3333 """
457 longstring,2,A Long String Variable,Nominal,Input,12,Left,A12,A12,
458 numeric,3,A Numeric Variable,Scale,Input,8,Right,F10.0,F10.0,9; 5; 999
459 date,4,A Date Variable,Scale,Input,8,Right,DATE11,DATE11,
460 dollar,5,A Dollar Variable,Scale,Input,8,Right,DOLLAR11.2,DOLLAR11.2,
461 datetime,6,A Datetime Variable,Scale,Input,8,Right,DATETIME17.0,DATETIME17.0,
464 Variable Value,,Label
465 A Short String Variable,1111,ones
468 A Numeric Variable,1,Unity
475 Table: Variable and Dataset Attributes
476 Variable and Name,,Value
477 A Numeric Variable,colour[1],blue
484 string,longstring,numeric,date,dollar,datetime
485 1111,One,1,01-JAN-2001,$1.00,01-JAN-2001 01:01
486 2222,Two,2,02-FEB-2002,$2.00,02-FEB-2002 02:02
487 3333,Three,3,03-MAR-2003,$3.00,03-MAR-2003 03:03
489 5555,Five,5,05-MAY-2005,$5.00,05-MAY-2005 05:05
492 Name,Position,Label,Measurement Level,Role,Width,Alignment,Print Format,Write Format,Missing Values
493 string,1,A Short String Variable,Nominal,Input,8,Left,A8,A8,"""3333 """
494 longstring,2,A Long String Variable,Nominal,Input,12,Left,A12,A12,
495 numeric,3,A Numeric Variable,Scale,Input,8,Right,F10.0,F10.0,9; 5; 999
496 date,4,A Date Variable,Scale,Input,8,Right,DATE11,DATE11,
497 dollar,5,A Dollar Variable,Scale,Input,8,Right,DOLLAR11.2,DOLLAR11.2,
498 datetime,6,A Datetime Variable,Scale,Input,8,Right,DATETIME17.0,DATETIME17.0,
501 Variable Value,,Label
502 A Short String Variable,1111,ones
505 A Numeric Variable,1,Unity
512 Table: Variable and Dataset Attributes
513 Variable and Name,,Value
514 A Numeric Variable,colour[1],blue
521 string,longstring,numeric,date,dollar,datetime
522 1111,One,1,01-JAN-2001,$1.00,01-JAN-2001 01:01
523 2222,Two,2,02-FEB-2002,$2.00,02-FEB-2002 02:02
524 3333,Three,3,03-MAR-2003,$3.00,03-MAR-2003 03:03
526 5555,Five,5,05-MAY-2005,$5.00,05-MAY-2005 05:05
530 AT_SETUP([Perl value formatting])
531 AT_SKIP_IF([test "$WITH_PERL_MODULE" = no])
533 [DATA LIST LIST /d (DATETIME17).
538 SAVE OUTFILE='dd.sav'.
540 AT_CHECK([pspp -O format=csv dd.sps], [0],
541 [Table: Reading free-form data from INLINE.
550 my $sf = PSPP::Reader->open ("dd.sav");
552 my $dict = $sf->get_dict ();
554 my (@c) = $sf->get_next_case ();
556 my $var = $dict->get_var (0);
558 my $formatted = PSPP::format_value ($val, $var);
559 my $str = gmtime ($val - PSPP::PERL_EPOCH);
560 print "Formatted string is \"$formatted\"\n";
561 print "Perl representation is \"$str\"\n";
563 AT_CHECK([RUN_PERL_MODULE test.pl], [0],
564 [[Formatted string is "11-SEP-2001 08:20"
565 Perl representation is "Tue Sep 11 08:20:00 2001"
569 AT_SETUP([Perl opening nonexistent file])
570 AT_SKIP_IF([test "$WITH_PERL_MODULE" = no])
576 my $sf = PSPP::Reader->open ("no-such-file.sav");
578 die "Returns undef on opening failure" if ref $sf;
579 print $PSPP::errstr, "\n";
581 AT_CHECK([RUN_PERL_MODULE test.pl], [0],
582 [[An error occurred while opening `no-such-file.sav': No such file or directory.
584 [[Name "PSPP::errstr" used only once: possible typo at test.pl line 8.
588 AT_SETUP([Perl missing values])
589 AT_SKIP_IF([test "$WITH_PERL_MODULE" = no])
590 PERL_GENERATE_SYSFILE
596 my $sf = PSPP::Reader->open ("sample.sav");
598 my $dict = $sf->get_dict ();
600 my (@c) = $sf->get_next_case ();
602 my $stringvar = $dict->get_var (0);
603 my $numericvar = $dict->get_var (2);
606 die "Missing Value Negative String"
607 if PSPP::value_is_missing ($val, $stringvar);
611 die "Missing Value Negative Num"
612 if PSPP::value_is_missing ($val, $numericvar);
614 @c = $sf->get_next_case ();
615 @c = $sf->get_next_case ();
618 die "Missing Value Positive"
619 if !PSPP::value_is_missing ($val, $stringvar);
621 @c = $sf->get_next_case ();
623 die "Missing Value Positive SYS"
624 if !PSPP::value_is_missing ($val, $numericvar);
626 @c = $sf->get_next_case ();
628 die "Missing Value Positive Num"
629 if !PSPP::value_is_missing ($val, $numericvar);
631 AT_CHECK([RUN_PERL_MODULE test.pl])
634 AT_SETUP([Perl custom attributes])
635 AT_SKIP_IF([test "$WITH_PERL_MODULE" = no])
636 PERL_GENERATE_SYSFILE
642 my $sf = PSPP::Reader->open ("sample.sav");
644 my $dict = $sf->get_dict ();
646 my $var = $dict->get_var_by_name ("numeric");
648 my $attr = $var->get_attributes ();
650 foreach my $k (sort (keys (%$attr)))
652 my $ll = $attr->{$k};
654 print map "$_\n", join ', ', @$ll;
657 AT_CHECK([RUN_PERL_MODULE test.pl], [0],
659 colour =>blue, pink, violet
660 nationality =>foreign
665 AT_SETUP([Perl Pspp.t])
666 AT_SKIP_IF([test "$WITH_PERL_MODULE" = no])
667 # Skip this test if Perl's Text::Diff module is not installed.
668 AT_CHECK([perl -MText::Diff -e '' || exit 77])
669 AT_CHECK([RUN_PERL_MODULE $abs_top_builddir/perl-module/t/Pspp.t], [0],
672 ok 2 - Dictionary Creation
674 ok 4 - Trap illegal variable name
676 ok 6 - Accept legal variable name
678 ok 8 - Trap duplicate variable name
680 ok 10 - Accept valid format
682 ok 12 - Create sysfile object
683 ok 13 - Write system file
685 ok 15 - Appending Case with too many variables
687 ok 17 - Append Case 2
690 ok 20 - Dictionary Creation 2
691 ok 21 - Value label for short string
692 ok 22 - Value label for long string
693 ok 23 - Check output 2
694 ok 24 - Dictionary survives sysfile
695 ok 25 - Basic reader operation
696 ok 26 - Streaming of files
697 Formatted string is "11-SEP-2001 08:20"
698 ok 27 - format_value function
699 ok 28 - Perl representation of time
700 ok 29 - Returns undef on opening failure
701 ok 30 - Error string on open failure
702 ok 31 - Missing Value Negative String
703 ok 32 - Missing Value Negative Num
704 ok 33 - Missing Value Positive
705 ok 34 - Missing Value Positive SYS
706 ok 35 - Missing Value Positive Num
707 ok 36 - Custom Attributes