import os, sys import tg, pylons import subprocess from webob.exc import HTTPNotFound from bazbase import conversion, translators, structure from bazki import getting, auth from bazki.translators import url from gameki import restricted, util def foreach_markup(list_expr, color=None, ancestor=None, group=None, owned=None, let='', propname=u'product', order_by=None): if let is True: varness = "o,ownr" let = "owner=ownr" else: varness = "o" # <><><> markup = "<>\n' % (u.ename, loopover) rg_element = u'e' exclude_base = 'exclude' markup += foreach_markup( "recursive_get(%s, 'stuff', '%s', %s, folded=False)" % (rg_element, exclude_base, u.ename), color, ancestor, group, owned=True, let=True, propname=propname) # For stuff that's not owned, don't set owner at all, so all # instances of the same item must be identical and get cached in the # same slot. markup += foreach_markup( "recursive_get(%s, 'stuff', '%s', folded=False)" % (rg_element, exclude_base), color, ancestor, group, owned=False, propname=propname) if (propname == u'product' and (color is not None or (ancestor is not None and ancestor.get_parent() is None) or (ancestor is None and group is None))): markup += "<>sys.stderr, markup if type == '.raw': ret = markup ctype = 'text/plain' else: try: flags = '' if no_headers: flags += 'h' ret = conversion.convert_markup(markup, type, global_metadata, cacheable_as='/print/%s/%s/%s/%s' % (user, name, mode, flags)) except conversion.ConversionFailedException,e: raise HTTPNotFound(e) ctype, enc = translators.guess_type(name+type) if not isinstance(ret,str): # TG doesn't like buffers or unicode. ret = str(ret) return ret, ctype class Printer(tg.TGController): @tg.expose(template="mako:gameki.templates.printing") def _default(self, user=None, name=None, mode=None, type=None, print_as=None, print_mode=None, no_headers=False): if user is None: if not pylons.request.url.endswith('/'): tg.redirect(pylons.request.url+'/') return {} if type is not None: pass elif name is None: user, type = getting.filename_split(user) elif mode is None: name, type = getting.filename_split(name) name = name.replace('_', ' ') name = unicode(name, 'utf-8') else: mode, type = getting.filename_split(mode) if not name: name = None if not mode: mode = None ret, ctype = print_stuff(user, name, mode, type, no_headers=no_headers) if ctype: try: pylons.response.headers['Content-type'] = ctype + '; charset=utf-8' except TypeError: pass return ret # Printing to lpr translator def lpr(im): printer = im.metadata()['filters']['P'] username = im.metadata()['filters']['U'] mode = im.metadata()['filters']['Z'] command_line = ['lpr', '-P%s' % printer, '-U%s' % username] if mode == 'duplex': command_line.append('-o') command_line.append('sides=two-sided-long-edge') elif mode == 'fronts': command_line.append('-o') command_line.append('page-set=odd') elif mode == 'backs': command_line.append('-o') command_line.append('page-set=even') else: assert False, mode # This is either a .pdf produced by LaTeX and thus already on disk # or data loaded from cache, which will be in memory. if im.data is None: command_line.append(im.asPath()) indata = '' else: indata = im.asData() p = subprocess.Popen(command_line, stdin=subprocess.PIPE, stdout=subprocess.PIPE, stderr=subprocess.PIPE) out, err = p.communicate(indata) im.setData('lpr returned: %s\n' % p.returncode + out + err, 'lpr') im.deps.makeUncacheable() translators.TRANSLATORS.setdefault('lpr', {})['.pdf'] = lpr