1 #! /usr/local/bin/python
3 # Watch line printer queues (only works with BSD 4.3 lpq).
5 # This brings up a window containing one line per printer argument.
7 # Each line gives a small summary of the printer's status and queue.
8 # The status tries to give as much relevant information as possible,
9 # and gives extra info if you have jobs in the queue.
11 # The line's background color gives a hint at the status: navajo white
12 # for idle, green if your job is now printing, yellow/orange for
13 # small/large queue, red for errors.
15 # To reduce the duration of the unresponsive time while it is waiting
16 # for an lpq subprocess to finish, it polls one printer every
17 # delay/len(printers) seconds. A tiny dot indicates the last printer
18 # updated. Hit the mouse button in the window to update the next one.
21 # - add an argument to override the default delay
22 # - add arguments to override the default colors
23 # - better heuristic for small/large queue (and more colors!)
24 # - mouse clicks should update the printer clicked in
25 # - better visual appearance, e.g., boxes around the lines?
33 from stdwinevents
import *
37 DEF_PRINTER
= 'oce' # This is CWI specific!
41 c_unknown
= stdwin
.fetchcolor('white')
42 c_idle
= stdwin
.fetchcolor('navajo white')
43 c_ontop
= stdwin
.fetchcolor('green')
44 c_smallqueue
= stdwin
.fetchcolor('yellow')
45 c_bigqueue
= stdwin
.fetchcolor('orange')
46 c_error
= stdwin
.fetchcolor('red')
52 thisuser
= posix
.environ
['LOGNAME']
54 thisuser
= posix
.environ
['USER']
56 printers
= sys
.argv
[1:]
58 # Strip '-P' from printer names just in case
59 # the user specified it...
60 for i
in range(len(printers
)):
61 if printers
[i
][:2] == '-P':
62 printers
[i
] = printers
[i
][2:]
64 if posix
.environ
.has_key('PRINTER'):
65 printers
= [posix
.environ
['PRINTER']]
67 printers
= [DEF_PRINTER
]
69 width
= stdwin
.textwidth('in')*20
70 height
= len(printers
) * stdwin
.lineheight() + 5
71 stdwin
.setdefwinsize(width
, height
)
72 stdwin
.setdefscrollbars(0, 0)
74 win
= stdwin
.open('lpwin')
76 win
.printers
= printers
77 win
.colors
= [c_unknown
] * len(printers
)
78 win
.texts
= printers
[:]
81 win
.thisuser
= thisuser
82 win
.dispatch
= lpdispatch
86 mainloop
.register(win
)
89 def lpdispatch(event
):
90 type, win
, detail
= event
91 if type == WE_CLOSE
or type == WE_CHAR
and detail
in ('q', 'Q'):
92 mainloop
.unregister(win
)
95 elif type == WE_TIMER
:
97 win
.change((0,0), (10000, 10000))
98 elif type == WE_MOUSE_UP
:
102 d
= win
.begindrawing()
103 offset
= d
.textwidth('.')
105 for i
in range(len(win
.printers
)):
107 color
= win
.colors
[i
]
109 d
.erase((h
, v
), (h
+10000, v
+d
.lineheight()))
110 if (i
+1) % len(win
.printers
) == win
.next
and color
<> c_unknown
:
112 d
.text((h
+offset
, v
), text
)
113 v
= v
+ d
.lineheight()
117 win
.next
= (i
+1) % len(win
.printers
)
118 win
.texts
[i
], win
.colors
[i
] = makestatus(win
.printers
[i
], win
.thisuser
)
119 win
.settimer(int(win
.delay
* 10.0 / len(win
.printers
)))
121 def makestatus(name
, thisuser
):
122 pipe
= posix
.popen('lpq -P' + name
+ ' 2>&1', 'r')
132 line
= pipe
.readline()
134 fields
= string
.split(line
)
136 if len(fields
) >= 6 and fields
[n
-1] == 'bytes':
141 bytes
= eval(fields
[n
-2])
147 aheadbytes
= aheadbytes
+ bytes
148 aheadjobs
= aheadjobs
+ 1
149 totalbytes
= totalbytes
+ bytes
150 totaljobs
= totaljobs
+ 1
151 if color
== c_unknown
:
153 elif color
== c_smallqueue
:
155 if users
.has_key(user
):
156 ujobs
, ubytes
= users
[user
]
160 ubytes
= ubytes
+ bytes
161 users
[user
] = ujobs
, ubytes
163 if fields
and fields
[0] <> 'Rank':
164 line
= string
.strip(line
)
165 if line
== 'no entries':
166 line
= name
+ ': idle'
167 if color
== c_unknown
:
169 elif line
[-22:] == ' is ready and printing':
172 line
= name
+ ': ' + line
177 line
= `
(totalbytes
+1023)/1024`
+ ' K'
178 if totaljobs
<> len(users
):
179 line
= line
+ ' (' + `totaljobs`
+ ' jobs)'
181 line
= line
+ ' for ' + users
.keys()[0]
183 line
= line
+ ' for ' + `
len(users
)`
+ ' users'
186 line
= line
+ ' (' + thisuser
+ ' first)'
188 line
= line
+ ' (' + `
(aheadbytes
+1023)/1024`
189 line
= line
+ ' K before ' + thisuser
+ ')'
194 lines
.append('lpq exit status ' + `sts`
)
196 return string
.joinfields(lines
, ': '), color