datefmt: Define 1 year as 365.2425 days instead of 365.25
[sunny256-utils.git] / tests / postgres.t
blobec85df07f666e409514916a87079412e176fef81
1 #!/usr/bin/env perl
3 #=======================================================================
4 # postgres.t
5 # File ID: 6c8dbc38-3b85-11e5-9db6-000df06acc56
7 # Test suite for postgres(1).
9 # Character set: UTF-8
10 # ©opyleft 2015– Øyvind A. Holm <sunny@sunbase.org>
11 # License: GNU General Public License version 2 or later, see end of
12 # file for legal stuff.
13 #=======================================================================
15 use strict;
16 use warnings;
18 use Test::More;
19 if (`createdb --version 2>/dev/null` !~ /PostgreSQL/) {
20 plan skip_all => "Postgres is not installed here";
21 } else {
22 plan "no_plan";
25 BEGIN {
26 # use_ok() goes here
29 use Getopt::Long;
31 local $| = 1;
33 our $CMDB = "";
34 our $CMD = "../$CMDB";
36 our %Opt = (
38 'all' => 0,
39 'help' => 0,
40 'quiet' => 0,
41 'todo' => 0,
42 'verbose' => 0,
43 'version' => 0,
47 our $progname = $0;
48 $progname =~ s/^.*\/(.*?)$/$1/;
49 our $VERSION = '0.0.0';
51 my %descriptions = ();
53 Getopt::Long::Configure('bundling');
54 GetOptions(
56 'all|a' => \$Opt{'all'},
57 'help|h' => \$Opt{'help'},
58 'quiet|q+' => \$Opt{'quiet'},
59 'todo|t' => \$Opt{'todo'},
60 'verbose|v+' => \$Opt{'verbose'},
61 'version' => \$Opt{'version'},
63 ) || die("$progname: Option error. Use -h for help.\n");
65 $Opt{'verbose'} -= $Opt{'quiet'};
66 $Opt{'help'} && usage(0);
67 if ($Opt{'version'}) {
68 print_version();
69 exit(0);
72 my $tmpdb = "tmp-postgres-t-$$-" . substr(rand, 2, 8);
73 my $tmp_stdout = '.tmp-postgres-t-stdout.tmp';
74 my $tmp_stderr = '.tmp-postgres-t-stderr.tmp';
76 exit(main());
78 sub main {
79 # {{{
80 my $Retval = 0;
82 diag(sprintf('========== Executing %s v%s ==========',
83 $progname, $VERSION));
85 if ($Opt{'todo'} && !$Opt{'all'}) {
86 goto todo_section;
89 =pod
91 testcmd("$CMD command", # {{{
92 <<'END',
93 [expected stdout]
94 END
95 '',
97 'description',
100 # }}}
102 =cut
104 testcmd("createdb \"$tmpdb\"", # {{{
108 'Create temporary database',
109 ) || BAIL_OUT("Cannot create temporary database, " .
110 "not much point in going on, then");
112 # }}}
113 diag('Make sure the db sorting uses C locale');
114 psql_cmd($tmpdb, # {{{
115 <<END,
116 CREATE TABLE t (s varchar);
117 COPY t FROM stdin;
125 øæ
128 ØØØØHH
130 ÆØ
131 ÅØÆ
139 🤘
144 indeed
147 '/^' .
148 'CREATE TABLE\n' .
149 'COPY 27\n' .
150 '$/',
151 '/^$/',
152 'Insert unsorted text into db',
155 # }}}
156 psql_cmd($tmpdb, # {{{
157 'COPY (SELECT * FROM t ORDER BY s) TO stdout;',
158 '/^' .
159 '\n' .
160 '12\n' .
161 'A\n' .
162 'B\n' .
163 'O\n' .
164 'X\n' .
165 'Y\n' .
166 'a\n' .
167 'f\n' .
168 'gh\n' .
169 'indeed\n' .
170 'o\n' .
171 'ser\n' .
172 'x\n' .
173 'y\n' .
174 \n' .
175 'ÅØÆ\n' .
176 'ÆØ\n' .
177 'ØØØØHH\n' .
178 \n' .
179 \n' .
180 \n' .
181 'øæ\n' .
182 '→\n' .
183 '☮\n' .
184 '❤\n' .
185 '🤘\n' .
186 '$/',
187 '/^$/',
188 'Text sorting follows the Unicode table',
191 # }}}
192 diag('Cleaning up...');
193 ok(unlink($tmp_stdout), 'Delete stdout tmpfile');
194 ok(unlink($tmp_stderr), 'Delete stderr tmpfile');
195 testcmd("dropdb \"$tmpdb\"", # {{{
199 'Drop temporary database',
202 # }}}
204 todo_section:
207 if ($Opt{'all'} || $Opt{'todo'}) {
208 diag('Running TODO tests...'); # {{{
210 TODO: {
212 local $TODO = '';
213 # Insert TODO tests here.
216 # TODO tests }}}
219 diag('Testing finished.');
220 return $Retval;
221 # }}}
222 } # main()
224 sub psql_cmd {
225 # {{{
226 my ($db, $sql, $exp_stdout, $exp_stderr, $desc) = @_;
227 ok(open(my $dbpipe, "| psql -X -d \"$tmpdb\" >$tmp_stdout 2>$tmp_stderr"),
228 "Open db pipe ($desc)");
229 ok(print($dbpipe $sql), "Print to pipe ($desc)");
230 ok(close($dbpipe), "Close db pipe ($desc)");
231 like(file_data($tmp_stdout), $exp_stdout, "$desc (stdout)");
232 like(file_data($tmp_stderr), $exp_stderr, "$desc (stderr)");
233 return;
234 # }}}
235 } # psql_cmd()
237 sub testcmd {
238 # {{{
239 my ($Cmd, $Exp_stdout, $Exp_stderr, $Exp_retval, $Desc) = @_;
240 defined($descriptions{$Desc}) &&
241 BAIL_OUT("testcmd(): '$Desc' description is used twice");
242 $descriptions{$Desc} = 1;
243 my $stderr_cmd = '';
244 my $cmd_outp_str = $Opt{'verbose'} >= 1 ? "\"$Cmd\" - " : '';
245 my $Txt = join('', $cmd_outp_str, defined($Desc) ? $Desc : '');
246 my $TMP_STDERR = "$CMDB-stderr.tmp";
247 my $retval = 1;
249 if (defined($Exp_stderr)) {
250 $stderr_cmd = " 2>$TMP_STDERR";
252 $retval &= is(`$Cmd$stderr_cmd`, $Exp_stdout, "$Txt (stdout)");
253 my $ret_val = $?;
254 if (defined($Exp_stderr)) {
255 $retval &= is(file_data($TMP_STDERR), $Exp_stderr, "$Txt (stderr)");
256 unlink($TMP_STDERR);
257 } else {
258 diag("Warning: stderr not defined for '$Txt'");
260 $retval &= is($ret_val >> 8, $Exp_retval, "$Txt (retval)");
262 return $retval;
263 # }}}
264 } # testcmd()
266 sub likecmd {
267 # {{{
268 my ($Cmd, $Exp_stdout, $Exp_stderr, $Exp_retval, $Desc) = @_;
269 defined($descriptions{$Desc}) &&
270 BAIL_OUT("likecmd(): '$Desc' description is used twice");
271 $descriptions{$Desc} = 1;
272 my $stderr_cmd = '';
273 my $cmd_outp_str = $Opt{'verbose'} >= 1 ? "\"$Cmd\" - " : '';
274 my $Txt = join('', $cmd_outp_str, defined($Desc) ? $Desc : '');
275 my $TMP_STDERR = "$CMDB-stderr.tmp";
276 my $retval = 1;
278 if (defined($Exp_stderr)) {
279 $stderr_cmd = " 2>$TMP_STDERR";
281 $retval &= like(`$Cmd$stderr_cmd`, $Exp_stdout, "$Txt (stdout)");
282 my $ret_val = $?;
283 if (defined($Exp_stderr)) {
284 $retval &= like(file_data($TMP_STDERR), $Exp_stderr, "$Txt (stderr)");
285 unlink($TMP_STDERR);
286 } else {
287 diag("Warning: stderr not defined for '$Txt'");
289 $retval &= is($ret_val >> 8, $Exp_retval, "$Txt (retval)");
291 return $retval;
292 # }}}
293 } # likecmd()
295 sub file_data {
296 # Return file content as a string {{{
297 my $File = shift;
298 my $Txt;
300 open(my $fp, '<', $File) or return undef;
301 local $/ = undef;
302 $Txt = <$fp>;
303 close($fp);
304 return $Txt;
305 # }}}
306 } # file_data()
308 sub print_version {
309 # Print program version {{{
310 print("$progname $VERSION\n");
311 return;
312 # }}}
313 } # print_version()
315 sub usage {
316 # Send the help message to stdout {{{
317 my $Retval = shift;
319 if ($Opt{'verbose'}) {
320 print("\n");
321 print_version();
323 print(<<"END");
325 Usage: $progname [options]
327 Contains tests for the $CMDB(1) program.
329 Options:
331 -a, --all
332 Run all tests, also TODOs.
333 -h, --help
334 Show this help.
335 -q, --quiet
336 Be more quiet. Can be repeated to increase silence.
337 -t, --todo
338 Run only the TODO tests.
339 -v, --verbose
340 Increase level of verbosity. Can be repeated.
341 --version
342 Print version information.
345 exit($Retval);
346 # }}}
347 } # usage()
349 sub msg {
350 # Print a status message to stderr based on verbosity level {{{
351 my ($verbose_level, $Txt) = @_;
353 $verbose_level > $Opt{'verbose'} && return;
354 print(STDERR "$progname: $Txt\n");
355 return;
356 # }}}
357 } # msg()
359 __END__
361 # This program is free software; you can redistribute it and/or modify
362 # it under the terms of the GNU General Public License as published by
363 # the Free Software Foundation; either version 2 of the License, or (at
364 # your option) any later version.
366 # This program is distributed in the hope that it will be useful, but
367 # WITHOUT ANY WARRANTY; without even the implied warranty of
368 # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
369 # See the GNU General Public License for more details.
371 # You should have received a copy of the GNU General Public License
372 # along with this program.
373 # If not, see L<http://www.gnu.org/licenses/>.
375 # vim: set fenc=UTF-8 ft=perl fdm=marker ts=4 sw=4 sts=4 et fo+=w :