Skip to content
Projects
Groups
Snippets
Help
Loading...
Help
Support
Keyboard shortcuts
?
Submit feedback
Contribute to GitLab
Sign in
Toggle navigation
E
exam-print-script
Project overview
Project overview
Details
Activity
Releases
Repository
Repository
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Issues
2
Issues
2
List
Boards
Labels
Milestones
Merge Requests
0
Merge Requests
0
CI / CD
CI / CD
Pipelines
Jobs
Schedules
Analytics
Analytics
CI / CD
Repository
Value Stream
Wiki
Wiki
Members
Members
Collapse sidebar
Close sidebar
Activity
Graph
Create a new issue
Jobs
Commits
Issue Boards
Open sidebar
A-SAM
exam-print-script
Commits
916f1285
Commit
916f1285
authored
Jan 31, 2020
by
Tandri Gauksson
Browse files
Options
Browse Files
Download
Email Patches
Plain Diff
A new print script, since the old print.sh was outdated and not working
parent
3a3a44fa
Changes
1
Hide whitespace changes
Inline
Side-by-side
Showing
1 changed file
with
131 additions
and
0 deletions
+131
-0
print.py
print.py
+131
-0
No files found.
print.py
0 → 100755
View file @
916f1285
#!/usr/bin/python3
"""
Usage: ./print.py /path/to/results
This script will print all <ip>.pdf files in /path/to/results in alphabetical
order* w.r.t the students' last names (as opposed to ip addresses).
A new directory /path/to/results/pdf_alphabetic of alphabetized (symlink)
pdfs is created, and can be safely deleted afterwards.
*Approximate alphabetical order, see create_symlinks.__doc__.
By default, the pdfs are printed double-sided, two pages per side,
and each student's solution is stapled. This can be configured in
the LPR_OPTIONS variable.
The default printer is p-hg-j-54. This can be configured in the PRINTER
variable.
Tip: Use "lpstat -p" to see the list of available printers.
The path/to/results should point to a directory containing the pdfs of
the student's solution, created by latex_creator.py, as well as the
candidates.csv for the <ip> -> <last name> mapping.
The pdfs should be named <ip>.pdf and other files, such as <ip>-nup.pdf,
out.pdf, out_rotated.pdf are ignored.
To do:
* Add --printer to command line arguments.
* Automatically split the job into batches, including a small test batch.
* Await user input before starting next batch. "Print next batch? (Y/n)".
* Allow a list of printers ["p-hg-j-42","p-hg-j-54",...] to print in
parallel. Make sure each printer gets consecutive batches, so that
the piles of paper can be easily joined while retaining the order.
"""
# Remove "-o StapleLocation=UpperRight" to skip stapling.
LPR_OPTIONS
=
"-o sides=two-sided-short-edge -o landscape -o fit-to-page -o media=A4 -o number-up=2 -o number-up-layout=lr -o StapleLocation=UpperRight"
# ~ PRINTER = "p-hg-j-54"
PRINTER
=
"p-hg-e-62-2"
import
sys
import
os
import
subprocess
import
csv
from
string
import
ascii_letters
def
format_status
(
string
):
start
=
'
\033
[92m'
#green
end
=
'
\033
[0m'
return
start
+
string
+
end
def
is_ip_pdf
(
fname
):
'''
Any <ip>.pdf will satisfy this condition, while out.pdf,
out_rotated.pdf, <ip>-nup.pdf, and non-pdf files are ignored.
Not actually checking if valid ip address.
'''
fname_split
=
fname
.
split
(
'.'
)
return
len
(
fname_split
)
>
1
and
fname_split
[
-
1
]
==
"pdf"
\
and
all
([
x
.
isdigit
()
for
x
in
fname_split
[:
-
1
]])
def
rm_non_ascii
(
name
):
# To do: instead of removing, replace non-ascii letters by their ascii alternatives.
allowed_letters
=
set
(
ascii_letters
)
return
""
.
join
([
letter
for
letter
in
name
if
letter
in
allowed_letters
])
def
create_symlinks
(
pdf_dir
):
'''
pdf_dir needs to contain candidates.csv
Creates a subdirectory of pdf_dir called pdf_alphabetic.
The new directory contains symbolic links to all <ip>.pdf files in pdf_dir,
with names <lastname>.<ip>.pdf, so that they are in alphabetic order.
The following caveats can cause interruptions of the alphabetic ordering:
Caveat 1: The <lastname> is provided by the student and sometimes the
student will instead give their first name.
Caveat 2: Any non-ascii characters of <lastname> are removed.
'''
pdf_dir
=
os
.
path
.
abspath
(
pdf_dir
)
file_list
=
os
.
listdir
(
pdf_dir
)
symlink_dir
=
os
.
path
.
abspath
(
pdf_dir
+
"/pdf_alphabetic"
)
if
not
os
.
path
.
isdir
(
symlink_dir
):
print
(
format_status
(
"Alphabetizing into directory:
\n\t
"
)
+
symlink_dir
)
os
.
mkdir
(
symlink_dir
)
# directory for for symlinks
else
:
print
(
format_status
(
"Overwriting existing alphabetized directory:
\n\t
"
)
+
symlink_dir
)
for
fname
in
file_list
:
if
is_ip_pdf
(
fname
):
pdf_ip
=
fname
[:
-
4
]
with
open
(
pdf_dir
+
"/candidates.csv"
)
as
csvfile
:
# Searching for the student's name.
candidates
=
csv
.
reader
(
csvfile
,
delimiter
=
';'
)
for
student
in
candidates
:
# student = [ <ip>, <login>, <fullname> ]
if
student
[
0
]
==
pdf_ip
:
student_name
=
student
[
2
]
.
split
()[
0
]
.
lower
()
student_name
=
rm_non_ascii
(
student_name
)
if
not
student_name
:
# if name contains no ascii characters (!!!)
# use login instead.
student_name
=
student
[
1
]
new_fname
=
student_name
+
'.'
+
fname
symlink_path
=
symlink_dir
+
'/'
+
new_fname
# print(fname + ' -> ' + new_fname)
if
os
.
path
.
exists
(
symlink_path
):
os
.
remove
(
symlink_path
)
os
.
symlink
(
pdf_dir
+
'/'
+
fname
,
symlink_path
)
return
symlink_dir
def
print_all
(
symlink_dir
):
lpr_command
=
"lpr -P {} {}"
.
format
(
PRINTER
,
LPR_OPTIONS
)
# Create a list of arguments instead of string.
lpr_command
=
lpr_command
.
split
()
# The path needs to be treated separately, in case any folder has
# a space in its name.
pdf_files
=
[
f
for
f
in
os
.
listdir
(
symlink_dir
)
if
f
[
-
4
:]
==
".pdf"
]
print
(
format_status
(
"Printing
%
d documents using:
\n\t
"
%
len
(
pdf_files
))
+
" "
.
join
(
lpr_command
)
+
" <filename>"
)
for
fname
in
pdf_files
:
# To glob (*.pdf), we need shell=True in subprocess.run().
# To avoid this, just print all .pdf in separate commands.
if
fname
[
-
4
:]
==
".pdf"
:
print
(
"."
,
end
=
""
)
subprocess
.
run
(
lpr_command
+
[
symlink_dir
+
'/'
+
fname
],
check
=
True
,
shell
=
False
)
print
(
format_status
(
"
\n
Print job started! Go check printer: "
)
+
PRINTER
)
if
__name__
==
"__main__"
:
if
len
(
sys
.
argv
)
>
1
and
os
.
path
.
isdir
(
sys
.
argv
[
1
]):
path_to_results
=
sys
.
argv
[
1
]
path_to_symlinks
=
create_symlinks
(
path_to_results
)
print_all
(
path_to_symlinks
)
else
:
print
(
"Please provide a valid /path/to/results."
)
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment