1# Test printing via CUPS.
2
3import ./make-test.nix ({pkgs, ... }: {
4 name = "printing";
5 meta = with pkgs.stdenv.lib.maintainers; {
6 maintainers = [ domenkozar eelco chaoflow jgeerds ];
7 };
8
9 nodes = {
10
11 server =
12 { ... }:
13 { services.printing.enable = true;
14 services.printing.listenAddresses = [ "*:631" ];
15 services.printing.defaultShared = true;
16 services.printing.extraConf =
17 ''
18 <Location />
19 Order allow,deny
20 Allow from all
21 </Location>
22 '';
23 networking.firewall.allowedTCPPorts = [ 631 ];
24 };
25
26 client =
27 { ... }:
28 { services.printing.enable = true;
29 };
30
31 };
32
33 testScript =
34 ''
35 startAll;
36
37 # Make sure that cups is up on both sides.
38 $server->waitForUnit("cups.service");
39 $client->waitForUnit("cups.service");
40 $client->sleep(10); # wait until cups is fully initialized
41 $client->succeed("lpstat -r") =~ /scheduler is running/ or die;
42 # Test that UNIX socket is used for connections.
43 $client->succeed("lpstat -H") =~ "/var/run/cups/cups.sock" or die;
44 # Test that HTTP server is available too.
45 $client->succeed("curl --fail http://localhost:631/");
46 $client->succeed("curl --fail http://server:631/");
47 $server->fail("curl --fail --connect-timeout 2 http://client:631/");
48
49 # Add a HP Deskjet printer connected via USB to the server.
50 $server->succeed("lpadmin -p DeskjetLocal -E -v usb://foobar/printers/foobar");
51
52 # Add it to the client as well via IPP.
53 $client->succeed("lpadmin -p DeskjetRemote -E -v ipp://server/printers/DeskjetLocal");
54 $client->succeed("lpadmin -d DeskjetRemote");
55
56 # Do some status checks.
57 $client->succeed("lpstat -a") =~ /DeskjetRemote accepting requests/ or die;
58 $client->succeed("lpstat -h server:631 -a") =~ /DeskjetLocal accepting requests/ or die;
59 $client->succeed("cupsdisable DeskjetRemote");
60 $client->succeed("lpq") =~ /DeskjetRemote is not ready.*no entries/s or die;
61 $client->succeed("cupsenable DeskjetRemote");
62 $client->succeed("lpq") =~ /DeskjetRemote is ready.*no entries/s or die;
63
64 # Test printing various file types.
65 foreach my $file ("${pkgs.groff.doc}/share/doc/*/examples/mom/penguin.pdf",
66 "${pkgs.groff.doc}/share/doc/*/meref.ps",
67 "${pkgs.cups.out}/share/doc/cups/images/cups.png",
68 "${pkgs.pcre.doc}/share/doc/pcre/pcre.txt")
69 {
70 $file =~ /([^\/]*)$/; my $fn = $1;
71
72 subtest "print $fn", sub {
73
74 # Print the file on the client.
75 $client->succeed("lp $file");
76 $client->sleep(10);
77 $client->succeed("lpq") =~ /active.*root.*$fn/ or die;
78
79 # Ensure that a raw PCL file appeared in the server's queue
80 # (showing that the right filters have been applied). Of
81 # course, since there is no actual USB printer attached, the
82 # file will stay in the queue forever.
83 $server->waitForFile("/var/spool/cups/d*-001");
84 $server->sleep(10);
85 $server->succeed("lpq -a") =~ /$fn/ or die;
86
87 # Delete the job on the client. It should disappear on the
88 # server as well.
89 $client->succeed("lprm");
90 $client->sleep(10);
91 $client->succeed("lpq -a") =~ /no entries/;
92 Machine::retry sub {
93 return 1 if $server->succeed("lpq -a") =~ /no entries/;
94 };
95 # The queue is empty already, so this should be safe.
96 # Otherwise, pairs of "c*"-"d*-001" files might persist.
97 $server->execute("rm /var/spool/cups/*");
98 };
99 }
100 '';
101})