Changeset 3437 for pkipplib/trunk

Show
Ignore:
Timestamp:
10/06/08 00:24:42 (16 years ago)
Author:
jerome
Message:

Removed spaces at EOL.

Location:
pkipplib/trunk
Files:
11 modified

Legend:

Unmodified
Added
Removed
  • pkipplib/trunk/bin/pksubscribe

    r45 r3437  
    11#! /usr/bin/env python 
    2 # -*- coding: UTF-8 -*- 
     2# -*- coding: utf-8 -*- 
    33# 
    44# pkipplib : IPP and CUPS support for Python 
     
    99# the Free Software Foundation, either version 3 of the License, or 
    1010# (at your option) any later version. 
    11 #  
     11# 
    1212# This program is distributed in the hope that it will be useful, 
    1313# but WITHOUT ANY WARRANTY; without even the implied warranty of 
    1414# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the 
    1515# GNU General Public License for more details. 
    16 #  
     16# 
    1717# You should have received a copy of the GNU General Public License 
    1818# along with this program.  If not, see <http://www.gnu.org/licenses/>. 
     
    2828import optparse 
    2929 
    30 from pkipplib import pkipplib         
    31      
    32 if __name__ == "__main__" :     
     30from pkipplib import pkipplib 
     31 
     32if __name__ == "__main__" : 
    3333    try : 
    3434        locale.setlocale(locale.LC_ALL, "") 
     
    4040        gettext.NullTranslations().install() 
    4141    parser = optparse.OptionParser(usage="pksubscribe [options] [subscriptions ids]") 
    42     parser.add_option("-v", "--version",  
    43                             action="store_true",  
     42    parser.add_option("-v", "--version", 
     43                            action="store_true", 
    4444                            dest="version", 
    4545                            help=_("show pksubscribe's version number and exit.")) 
    46     parser.add_option("-c", "--cups",  
    47                             default="http://localhost:631",  
     46    parser.add_option("-c", "--cups", 
     47                            default="http://localhost:631", 
    4848                            dest="cups", 
    4949                            help=_("the CUPS server to connect to. Defaults to http://localhost:631")) 
    50     parser.add_option("-d", "--debug",  
    51                             action="store_true",  
     50    parser.add_option("-d", "--debug", 
     51                            action="store_true", 
    5252                            dest="debug", 
    5353                            help=_("activate debug mode.")) 
    54     parser.add_option("-X", "--delete",  
    55                             action="store_true",  
     54    parser.add_option("-X", "--delete", 
     55                            action="store_true", 
    5656                            dest="delete", 
    5757                            help=_("deletes subscriptions.")) 
    58     parser.add_option("-p", "--printer",  
     58    parser.add_option("-p", "--printer", 
    5959                            dest="printer", 
    6060                            help=_("the printer's name for a printer subscription.")) 
    61     parser.add_option("-j", "--job",  
    62                             type="int",  
     61    parser.add_option("-j", "--job", 
     62                            type="int", 
    6363                            dest="job", 
    6464                            help=_("the job's id for a job subscripition.")) 
    65     parser.add_option("-r", "--recipient",                         
     65    parser.add_option("-r", "--recipient", 
    6666                            dest="recipient", 
    6767                            help=_("the recipient's uri.")) 
    68     parser.add_option("-C", "--charset",                         
     68    parser.add_option("-C", "--charset", 
    6969                            dest="charset", 
    7070                            help=_("the charset to use in notifications sent for this subscription.")) 
    71     parser.add_option("-L", "--language",                         
     71    parser.add_option("-L", "--language", 
    7272                            dest="language", 
    7373                            help=_("the language to use in notifications sent for this subscription.")) 
    74     parser.add_option("-u", "--userdata",                         
     74    parser.add_option("-u", "--userdata", 
    7575                            dest="userdata", 
    7676                            help=_("the user's data to use in notifications for this subscription.")) 
    77     parser.add_option("-U", "--username",                         
     77    parser.add_option("-U", "--username", 
    7878                            dest="username", 
    7979                            help=_("the user's name to use when connecting to the CUPS server.")) 
    80     parser.add_option("-W", "--password",                         
     80    parser.add_option("-W", "--password", 
    8181                            dest="password", 
    8282                            help=_("the user's password to use when connecting to the CUPS server.")) 
    83     parser.add_option("-E", "--events",                         
     83    parser.add_option("-E", "--events", 
    8484                            dest="events", 
    8585                            help=_("a comma separated list of events to subscribe to.")) 
    86     parser.add_option("-P", "--pullmethod",                         
     86    parser.add_option("-P", "--pullmethod", 
    8787                            dest="pullmethod", 
    8888                            help=_("the optional pull method's name.")) 
     
    9191                            dest="duration", 
    9292                            help=_("the duration of the subscription.")) 
    93     parser.add_option("-I", "--interval",                         
     93    parser.add_option("-I", "--interval", 
    9494                            type="int", 
    9595                            dest="interval", 
    9696                            help=_("the time interval of the subscription.")) 
    97                              
     97 
    9898    (options, arguments) = parser.parse_args() 
    9999    if options.version : 
     
    102102        if not options.events and not options.delete : 
    103103            sys.stderr.write(_("You MUST pass a list of events to subscribe to.\n")) 
    104         elif not options.recipient and not options.delete :     
     104        elif not options.recipient and not options.delete : 
    105105            sys.stderr.write(_("You MUST pass a recipient for the subscription.\n")) 
    106         elif options.delete and not arguments :     
     106        elif options.delete and not arguments : 
    107107            sys.stderr.write(_("You MUST pass a subscriptions ids at the end of your command line.\n")) 
    108         else :     
     108        else : 
    109109            cups = pkipplib.CUPS(options.cups, 
    110110                                 options.username, 
     
    112112                                 debug=options.debug) 
    113113            baseurl = options.cups.replace("http://", "ipp://") 
    114             if baseurl.endswith(":631") :  
     114            if baseurl.endswith(":631") : 
    115115                baseurl = baseurl[:-4] 
    116116            if options.printer : 
    117117                url = "%s/printers/%s" % (baseurl, options.printer) 
    118             elif options.job :      
     118            elif options.job : 
    119119                url = "%s/jobs/%i" % (baseurl, options.job) 
    120             else :     
     120            else : 
    121121                url = baseurl 
    122             if not options.delete :     
     122            if not options.delete : 
    123123                answer = cups.createSubscription(url, 
    124124                                                 [e.strip() for e in options.events.split(",")], 
     
    131131                                                 timeinterval=options.interval, 
    132132                                                 jobid=options.job) 
    133                 try :                                  
     133                try : 
    134134                    subscriptionid = answer.subscription["notify-subscription-id"][0][1] 
    135135                except KeyError : 
    136136                    sys.stderr.write("%s\n" % answer.operation["status-message"][0][1]) 
    137                 else :     
     137                else : 
    138138                    print _("Subscription %i registered.") % subscriptionid 
    139             else :         
     139            else : 
    140140                for subid in [int(arg) for arg in arguments] : 
    141141                    answer = cups.cancelSubscription(url, subid, options.job) 
     
    143143                        try : 
    144144                            error = answer.operation["status-message"][0][1] 
    145                         except KeyError :     
     145                        except KeyError : 
    146146                            print _("Subscription %i cancelled.") % subid 
    147147                        else : 
    148148                            sys.stderr.write("%s\n" % error) 
    149                     else :         
     149                    else : 
    150150                        sys.stderr.write(_("Incorrect answer (None)\n")) 
    151151 
  • pkipplib/trunk/clean.sh

    r45 r3437  
    1 #! /bin/sh 
     1y#! /bin/sh 
    22# 
    33# pkipplib : IPP support for Python 
     
    88# the Free Software Foundation, either version 3 of the License, or 
    99# (at your option) any later version. 
    10 #  
     10# 
    1111# This program is distributed in the hope that it will be useful, 
    1212# but WITHOUT ANY WARRANTY; without even the implied warranty of 
    1313# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the 
    1414# GNU General Public License for more details. 
    15 #  
     15# 
    1616# You should have received a copy of the GNU General Public License 
    1717# along with this program.  If not, see <http://www.gnu.org/licenses/>. 
  • pkipplib/trunk/MANIFEST.in

    r36 r3437  
    1 include README COPYING NEWS MANIFEST.in clean.sh bin/pksubscribe 
     1yinclude README COPYING NEWS MANIFEST.in clean.sh bin/pksubscribe 
    22recursive-include notifiers * 
  • pkipplib/trunk/notifiers/samplenotifier

    r45 r3437  
    11#! /usr/bin/env python 
    2 # -*- coding: UTF-8 -*- 
     2# -*- coding: utf-8 -*- 
    33# 
    44# pkipplib : IPP and CUPS support for Python 
     
    99# the Free Software Foundation, either version 3 of the License, or 
    1010# (at your option) any later version. 
    11 #  
     11# 
    1212# This program is distributed in the hope that it will be useful, 
    1313# but WITHOUT ANY WARRANTY; without even the implied warranty of 
    1414# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the 
    1515# GNU General Public License for more details. 
    16 #  
     16# 
    1717# You should have received a copy of the GNU General Public License 
    1818# along with this program.  If not, see <http://www.gnu.org/licenses/>. 
     
    3838    # First thing we do is put stdin in non-blocking mode. 
    3939    fd = sys.stdin.fileno() 
    40     fcntl.fcntl(sys.stdin.fileno(), fcntl.F_SETFL,  
     40    fcntl.fcntl(sys.stdin.fileno(), fcntl.F_SETFL, 
    4141                    fcntl.fcntl(fd, fcntl.F_GETFL) | os.O_NONBLOCK) 
    4242 
    4343    # then we read the notification CUPS sent us to our stdin 
    4444    notification = pkipplib.IPPRequest(sys.stdin.read()) 
    45      
     45 
    4646    # now we parse it 
    4747    notification.parse() 
    48      
     48 
    4949    # then we act one way or another, depending on the event received. 
    5050    event = notification.event_notification["notify-subscribed-event"][0][1] 
     
    5353        if event.endswith("-added") : 
    5454            action = "add" 
    55         else :     
     55        else : 
    5656            action = "delete" 
    5757        os.system('/usr/bin/pkprinters --%s "%s"' % (action, printername)) 
  • pkipplib/trunk/pkipplib/__init__.py

    r45 r3437  
    1 # -*- coding: UTF-8 -*- 
     1# -*- coding: utf-8 -*- 
    22# 
    33# pkipplib : IPP and CUPS support for Python 
     
    88# the Free Software Foundation, either version 3 of the License, or 
    99# (at your option) any later version. 
    10 #  
     10# 
    1111# This program is distributed in the hope that it will be useful, 
    1212# but WITHOUT ANY WARRANTY; without even the implied warranty of 
    1313# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the 
    1414# GNU General Public License for more details. 
    15 #  
     15# 
    1616# You should have received a copy of the GNU General Public License 
    1717# along with this program.  If not, see <http://www.gnu.org/licenses/>. 
  • pkipplib/trunk/pkipplib/pkipplib.py

    r45 r3437  
    11#! /usr/bin/env python 
    2 # -*- coding: UTF-8 -*- 
     2# -*- coding: utf-8 -*- 
    33# 
    44# pkipplib : IPP and CUPS support for Python 
     
    99# the Free Software Foundation, either version 3 of the License, or 
    1010# (at your option) any later version. 
    11 #  
     11# 
    1212# This program is distributed in the hope that it will be useful, 
    1313# but WITHOUT ANY WARRANTY; without even the implied warranty of 
    1414# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the 
    1515# GNU General Public License for more details. 
    16 #  
     16# 
    1717# You should have received a copy of the GNU General Public License 
    1818# along with this program.  If not, see <http://www.gnu.org/licenses/>. 
     
    238238IPP_MULTIPLE_JOBS_NOT_SUPPORTED = 0x0509 
    239239IPP_PRINTER_IS_DEACTIVATED = 0x50a 
    240    
     240 
    241241CUPS_PRINTER_LOCAL = 0x0000 
    242242CUPS_PRINTER_CLASS = 0x0001 
     
    265265CUPS_PRINTER_COMMANDS = 0x8000 
    266266CUPS_PRINTER_OPTIONS = 0xe6ff 
    267    
    268    
     267 
     268 
    269269class IPPError(Exception) : 
    270270    """An exception for IPP related stuff.""" 
     
    282282        self.request = request 
    283283        self.name = name 
    284          
     284 
    285285    def __setitem__(self, key, value) : 
    286286        """Appends the value to the real attribute.""" 
     
    293293                    attribute[j][1].append(value) 
    294294                    return 
    295             attribute.append((key, [value]))         
    296              
     295            attribute.append((key, [value])) 
     296 
    297297    def __getitem__(self, key) : 
    298298        """Returns an attribute's value.""" 
     
    307307        if answer : 
    308308            return answer 
    309         raise KeyError, key             
    310      
     309        raise KeyError, key 
     310 
    311311class IPPRequest : 
    312312    """A class for IPP requests.""" 
    313313    attributes_types = ("operation", "job", "printer", "unsupported", \ 
    314314                                     "subscription", "event_notification") 
    315     def __init__(self, data="", version=IPP_VERSION,  
     315    def __init__(self, data="", version=IPP_VERSION, 
    316316                                operation_id=None, \ 
    317317                                request_id=None, \ 
    318318                                debug=False) : 
    319319        """Initializes an IPP Message object. 
    320          
     320 
    321321           Parameters : 
    322             
     322 
    323323             data : the complete IPP Message's content. 
    324324             debug : a boolean value to output debug info on stderr. 
     
    327327        self._data = data 
    328328        self.parsed = False 
    329          
     329 
    330330        # Initializes message 
    331         self.setVersion(version)                 
     331        self.setVersion(version) 
    332332        self.setOperationId(operation_id) 
    333333        self.setRequestId(request_id) 
    334334        self.data = "" 
    335          
     335 
    336336        for attrtype in self.attributes_types : 
    337337            setattr(self, "_%s_attributes" % attrtype, [[]]) 
    338          
    339         # Initialize tags     
     338 
     339        # Initialize tags 
    340340        self.tags = [ None ] * 256 # by default all tags reserved 
    341          
     341 
    342342        # Delimiter tags 
    343343        self.tags[0x01] = "operation-attributes-tag" 
     
    348348        self.tags[0x06] = "subscription-attributes-tag" 
    349349        self.tags[0x07] = "event_notification-attributes-tag" 
    350          
     350 
    351351        # out of band values 
    352352        self.tags[0x10] = "unsupported" 
     
    357357        self.tags[0x16] = "delete-attribute" 
    358358        self.tags[0x17] = "admin-define" 
    359    
     359 
    360360        # integer values 
    361361        self.tags[0x20] = "generic-integer" 
     
    363363        self.tags[0x22] = "boolean" 
    364364        self.tags[0x23] = "enum" 
    365          
     365 
    366366        # octetString 
    367367        self.tags[0x30] = "octetString-with-an-unspecified-format" 
     
    373373        self.tags[0x36] = "nameWithLanguage" 
    374374        self.tags[0x37] = "endCollection" 
    375          
     375 
    376376        # character strings 
    377377        self.tags[0x40] = "generic-character-string" 
     
    385385        self.tags[0x49] = "mimeMediaType" 
    386386        self.tags[0x4a] = "memberAttrName" 
    387          
     387 
    388388        # Reverse mapping to generate IPP messages 
    389389        self.tagvalues = {} 
     
    392392            if value is not None : 
    393393                self.tagvalues[value] = i 
    394                                       
    395     def __getattr__(self, name) :                                  
     394 
     395    def __getattr__(self, name) : 
    396396        """Fakes attribute access.""" 
    397397        if name in self.attributes_types : 
     
    399399        else : 
    400400            raise AttributeError, name 
    401              
    402     def __str__(self) :         
     401 
     402    def __str__(self) : 
    403403        """Returns the parsed IPP message in a readable form.""" 
    404404        if not self.parsed : 
     
    414414                for (name, value) in attribute : 
    415415                    mybuffer.append("  %s : %s" % (name, value)) 
    416         if self.data :             
     416        if self.data : 
    417417            mybuffer.append("IPP datas : %s" % repr(self.data)) 
    418418        return "\n".join(mybuffer) 
    419          
    420     def logDebug(self, msg) :     
     419 
     420    def logDebug(self, msg) : 
    421421        """Prints a debug message.""" 
    422422        if self.debug : 
    423423            sys.stderr.write("%s\n" % msg) 
    424424            sys.stderr.flush() 
    425              
     425 
    426426    def setVersion(self, version) : 
    427427        """Sets the request's operation id.""" 
     
    432432                if len(version) == 2 : # 2-tuple 
    433433                    self.version = version 
    434                 else :     
     434                else : 
    435435                    try : 
    436436                        self.version = [int(p) for p in str(float(version)).split(".")] 
    437437                    except : 
    438438                        self.version = [int(p) for p in IPP_VERSION.split(".")] 
    439          
    440     def setOperationId(self, opid) :         
     439 
     440    def setOperationId(self, opid) : 
    441441        """Sets the request's operation id.""" 
    442442        self.operation_id = opid 
    443          
    444     def setRequestId(self, reqid) :         
     443 
     444    def setRequestId(self, reqid) : 
    445445        """Sets the request's request id.""" 
    446446        self.request_id = reqid 
    447          
    448     def dump(self) :     
     447 
     448    def dump(self) : 
    449449        """Generates an IPP Message. 
    450          
     450 
    451451           Returns the message as a string of text. 
    452         """     
     452        """ 
    453453        mybuffer = [] 
    454454        if None not in (self.version, self.operation_id) : 
     
    468468                                mybuffer.append(attrname) 
    469469                                nameprinted = 1 
    470                             else :      
     470                            else : 
    471471                                mybuffer.append(pack(">H", 0)) 
    472472                            if vtype in ("integer", "enum") : 
     
    476476                                mybuffer.append(pack(">H", 1)) 
    477477                                mybuffer.append(chr(val)) 
    478                             else :     
     478                            else : 
    479479                                mybuffer.append(pack(">H", len(val))) 
    480480                                mybuffer.append(val) 
    481481            mybuffer.append(chr(self.tagvalues["end-of-attributes-tag"])) 
    482         mybuffer.append(self.data)     
     482        mybuffer.append(self.data) 
    483483        return "".join(mybuffer) 
    484              
     484 
    485485    def parse(self) : 
    486486        """Parses an IPP Request. 
    487          
     487 
    488488           NB : Only a subset of RFC2910 is implemented. 
    489489        """ 
    490490        self._curname = None 
    491491        self._curattributes = None 
    492          
     492 
    493493        try : 
    494494            self.setVersion((ord(self._data[0]), ord(self._data[1]))) 
     
    509509                        self.position -= 1 
    510510                        continue 
    511                 oldtag = tag         
     511                oldtag = tag 
    512512                tag = ord(self._data[self.position]) 
    513513                if tag == oldtag : 
     
    515515        except IndexError : 
    516516            raise IPPError, "Unexpected end of IPP message." 
    517              
    518         self.data = self._data[self.position+1:]             
     517 
     518        self.data = self._data[self.position+1:] 
    519519        self.parsed = True 
    520          
    521     def parseTag(self) :     
     520 
     521    def parseTag(self) : 
    522522        """Extracts information from an IPP tag.""" 
    523523        pos = self.position 
     
    528528        if not namelength : 
    529529            name = self._curname 
    530         else :     
     530        else : 
    531531            posend += namelength 
    532532            self._curname = name = self._data[pos2:posend] 
     
    537537        if tagtype in ("integer", "enum") : 
    538538            value = unpack(">I", value)[0] 
    539         elif tagtype == "boolean" :     
     539        elif tagtype == "boolean" : 
    540540            value = ord(value) 
    541         try :     
     541        try : 
    542542            (oldname, oldval) = self._curattributes[-1][-1] 
    543543            if oldname == name : 
    544544                oldval.append((tagtype, value)) 
    545             else :     
     545            else : 
    546546                raise IndexError 
    547         except IndexError :     
     547        except IndexError : 
    548548            self._curattributes[-1].append((name, [(tagtype, value)])) 
    549549        self.logDebug("%s(%s) : %s" % (name, tagtype, value)) 
    550550        return posend - self.position 
    551          
    552     def operation_attributes_tag(self) :  
     551 
     552    def operation_attributes_tag(self) : 
    553553        """Indicates that the parser enters into an operation-attributes-tag group.""" 
    554554        self._curattributes = self._operation_attributes 
    555555        return self.parseTag() 
    556          
    557     def job_attributes_tag(self) :  
     556 
     557    def job_attributes_tag(self) : 
    558558        """Indicates that the parser enters into a job-attributes-tag group.""" 
    559559        self._curattributes = self._job_attributes 
    560560        return self.parseTag() 
    561          
    562     def printer_attributes_tag(self) :  
     561 
     562    def printer_attributes_tag(self) : 
    563563        """Indicates that the parser enters into a printer-attributes-tag group.""" 
    564564        self._curattributes = self._printer_attributes 
    565565        return self.parseTag() 
    566          
    567     def unsupported_attributes_tag(self) :  
     566 
     567    def unsupported_attributes_tag(self) : 
    568568        """Indicates that the parser enters into an unsupported-attributes-tag group.""" 
    569569        self._curattributes = self._unsupported_attributes 
    570570        return self.parseTag() 
    571          
    572     def subscription_attributes_tag(self) :  
     571 
     572    def subscription_attributes_tag(self) : 
    573573        """Indicates that the parser enters into a subscription-attributes-tag group.""" 
    574574        self._curattributes = self._subscription_attributes 
    575575        return self.parseTag() 
    576          
    577     def event_notification_attributes_tag(self) :  
     576 
     577    def event_notification_attributes_tag(self) : 
    578578        """Indicates that the parser enters into an event-notification-attributes-tag group.""" 
    579579        self._curattributes = self._event_notification_attributes 
    580580        return self.parseTag() 
    581          
    582              
     581 
     582 
    583583class CUPS : 
    584584    """A class for a CUPS instance.""" 
     
    589589            if self.url.endswith("/") : 
    590590                self.url = self.url[:-1] 
    591         else :         
     591        else : 
    592592            self.url = self.getDefaultURL() 
    593              
     593 
    594594        # If no username or password, use the ones set by CUPS, if any 
    595595        self.username = username or os.environ.get("AUTH_USERNAME") 
    596596        self.password = password or os.environ.get("AUTH_PASSWORD") 
    597          
     597 
    598598        self.charset = charset 
    599599        self.language = language 
     
    602602        self.lastErrorMessage = None 
    603603        self.requestId = None 
    604          
    605     def getDefaultURL(self) :     
     604 
     605    def getDefaultURL(self) : 
    606606        """Builds a default URL.""" 
    607607        # TODO : encryption methods. 
     
    613613            return "http://localhost:%s" % port 
    614614            #return "socket:%s" % server # TODO : make this work ! 
    615         else :     
     615        else : 
    616616            return "http://%s:%s" % (server, port) 
    617              
     617 
    618618    def identifierToURI(self, service, ident) : 
    619619        """Transforms an identifier into a particular URI depending on requested service.""" 
     
    621621                             service, 
    622622                             ident) 
    623          
    624     def nextRequestId(self) :         
     623 
     624    def nextRequestId(self) : 
    625625        """Increments the current request id and returns the new value.""" 
    626626        try : 
    627627            self.requestId += 1 
    628         except TypeError :     
     628        except TypeError : 
    629629            self.requestId = 1 
    630630        return self.requestId 
    631              
     631 
    632632    def newRequest(self, operationid=None) : 
    633633        """Generates a new empty request.""" 
     
    641641                req.operation["requesting-user-name"] = ("nameWithoutLanguage", self.username) 
    642642            return req 
    643      
     643 
    644644    def doRequest(self, req, url=None) : 
    645645        """Sends a request to the CUPS server. 
    646646           returns a new IPPRequest object, containing the parsed answer. 
    647         """    
     647        """ 
    648648        url = url or self.url 
    649649        connection = urllib2.Request(url=url, \ 
     
    657657                                   self.username, \ 
    658658                                   self.password or "") 
    659             authhandler = urllib2.HTTPBasicAuthHandler(pwmanager)                        
     659            authhandler = urllib2.HTTPBasicAuthHandler(pwmanager) 
    660660            opener = urllib2.build_opener(authhandler) 
    661661            urllib2.install_opener(opener) 
    662         else : # TODO : also do this in the 'if' part      
    663             if url.startswith("socket:") :  
     662        else : # TODO : also do this in the 'if' part 
     663            if url.startswith("socket:") : 
    664664                class SocketHandler(urllib2.HTTPHandler) : 
    665665                    """A class to handle IPP connections over an Unix domain socket.""" 
     
    675675                        sys.stderr.write("Opened [%s]\n" % req.get_selector()) 
    676676                        return s.makefile(mode="r+b") 
    677                          
    678                 opener = urllib2.build_opener(SocketHandler())   
     677 
     678                opener = urllib2.build_opener(SocketHandler()) 
    679679                urllib2.install_opener(opener) 
    680680                sys.stderr.write("Opener installed\n") 
    681         self.lastError = None     
     681        self.lastError = None 
    682682        self.lastErrorMessage = None 
    683         try :     
     683        try : 
    684684            response = urllib2.urlopen(connection) 
    685         except (urllib2.URLError, urllib2.HTTPError, socket.error), error :     
     685        except (urllib2.URLError, urllib2.HTTPError, socket.error), error : 
    686686            self.lastError = error 
    687687            self.lastErrorMessage = str(error) 
    688688            return None 
    689         else :     
     689        else : 
    690690            bytes = [] 
    691691            try : 
     
    694694                        try : 
    695695                            byte = response.read(1) 
    696                         except AttributeError :     
     696                        except AttributeError : 
    697697                            byte = response.recv(1) 
    698698                        if not byte : 
    699699                            break 
    700                         else :     
     700                        else : 
    701701                            bytes.append(byte) 
    702702                except socket.error : 
     
    711711            else : 
    712712                return None 
    713      
    714     def getPPD(self, queuename) :     
     713 
     714    def getPPD(self, queuename) : 
    715715        """Retrieves the PPD for a particular queuename.""" 
    716716        req = self.newRequest(IPP_GET_PRINTER_ATTRIBUTES) 
     
    719719            req.operation["requested-attributes"] = ("nameWithoutLanguage", attrib) 
    720720        return self.doRequest(req)  # TODO : get the PPD from the actual print server 
    721          
     721 
    722722    def getDefault(self) : 
    723723        """Retrieves CUPS' default printer.""" 
    724724        return self.doRequest(self.newRequest(CUPS_GET_DEFAULT)) 
    725      
    726     def getJobAttributes(self, jobid) :     
     725 
     726    def getJobAttributes(self, jobid) : 
    727727        """Retrieves a print job's attributes.""" 
    728728        req = self.newRequest(IPP_GET_JOB_ATTRIBUTES) 
    729729        req.operation["job-uri"] = ("uri", self.identifierToURI("jobs", jobid)) 
    730730        return self.doRequest(req) 
    731          
    732     def getPrinters(self) :     
     731 
     732    def getPrinters(self) : 
    733733        """Returns the list of print queues names.""" 
    734734        req = self.newRequest(CUPS_GET_PRINTERS) 
     
    737737        req.operation["printer-type-mask"] = ("enum", CUPS_PRINTER_CLASS) 
    738738        return [printer[1] for printer in self.doRequest(req).printer["printer-name"]] 
    739          
    740     def getDevices(self) :     
     739 
     740    def getDevices(self) : 
    741741        """Returns a list of devices as (deviceclass, deviceinfo, devicemakeandmodel, deviceuri) tuples.""" 
    742742        answer = self.doRequest(self.newRequest(CUPS_GET_DEVICES)) 
     
    745745                   [d[1] for d in answer.printer["device-make-and-model"]], \ 
    746746                   [d[1] for d in answer.printer["device-uri"]]) 
    747                     
    748     def getPPDs(self) :     
     747 
     748    def getPPDs(self) : 
    749749        """Returns a list of PPDs as (ppdnaturallanguage, ppdmake, ppdmakeandmodel, ppdname) tuples.""" 
    750750        answer = self.doRequest(self.newRequest(CUPS_GET_PPDS)) 
     
    753753                   [d[1] for d in answer.printer["ppd-make-and-model"]], \ 
    754754                   [d[1] for d in answer.printer["ppd-name"]]) 
    755                     
     755 
    756756    def createSubscription(self, uri, events=["all"], 
    757757                                      userdata=None, 
     
    764764                                      jobid=None) : 
    765765        """Creates a job, printer or server subscription. 
    766           
     766 
    767767           uri : the subscription's uri, e.g. ipp://server 
    768768           events : a list of events to subscribe to, e.g. ["printer-added", "printer-deleted"] 
     
    774774           timeinterval : the interval of time during notifications 
    775775           jobid : the optional job id in case of a job subscription 
    776         """    
     776        """ 
    777777        if jobid is not None : 
    778778            opid = IPP_CREATE_JOB_SUBSCRIPTION 
     
    785785        for event in events : 
    786786            req.subscription["notify-events"] = ("keyword", event) 
    787         if userdata is not None :     
     787        if userdata is not None : 
    788788            req.subscription["notify-user-data"] = ("octetString-with-an-unspecified-format", userdata) 
    789         if recipient is not None :     
     789        if recipient is not None : 
    790790            req.subscription["notify-recipient"] = ("uri", recipient) 
    791791        if pullmethod is not None : 
     
    802802            req.subscription["notify-job-id"] = ("integer", jobid) 
    803803        return self.doRequest(req) 
    804              
    805     def cancelSubscription(self, uri, subscriptionid, jobid=None) :     
     804 
     805    def cancelSubscription(self, uri, subscriptionid, jobid=None) : 
    806806        """Cancels a subscription. 
    807          
     807 
    808808           uri : the subscription's uri. 
    809809           subscriptionid : the subscription's id. 
     
    818818        req.event_notification["notify-subscription-id"] = ("integer", subscriptionid) 
    819819        return self.doRequest(req) 
    820          
    821 if __name__ == "__main__" :             
     820 
     821if __name__ == "__main__" : 
    822822    if (len(sys.argv) < 2) or (sys.argv[1] == "--debug") : 
    823823        print "usage : python pkipplib.py /var/spool/cups/c00005 [--debug] (for example)\n" 
    824     else :     
     824    else : 
    825825        infile = open(sys.argv[1], "rb") 
    826826        filedata = infile.read() 
    827827        infile.close() 
    828          
     828 
    829829        msg = IPPRequest(filedata, debug=(sys.argv[-1]=="--debug")) 
    830830        msg.parse() 
     
    832832        msg2.parse() 
    833833        filedata2 = msg2.dump() 
    834          
     834 
    835835        if filedata == filedata2 : 
    836836            print "Test OK : parsing original and parsing the output of the dump produce the same dump !" 
    837837            print str(msg) 
    838         else :     
     838        else : 
    839839            print "Test Failed !" 
    840840            print str(msg) 
    841841            print 
    842842            print str(msg2) 
    843          
     843 
  • pkipplib/trunk/pkipplib/version.py

    r45 r3437  
    1 # -*- coding: UTF-8 -*- 
     1# -*- coding: utf-8 -*- 
    22# 
    33# pkipplib : IPP and CUPS support for Python 
     
    88# the Free Software Foundation, either version 3 of the License, or 
    99# (at your option) any later version. 
    10 #  
     10# 
    1111# This program is distributed in the hope that it will be useful, 
    1212# but WITHOUT ANY WARRANTY; without even the implied warranty of 
    1313# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the 
    1414# GNU General Public License for more details. 
    15 #  
     15# 
    1616# You should have received a copy of the GNU General Public License 
    1717# along with this program.  If not, see <http://www.gnu.org/licenses/>. 
  • pkipplib/trunk/README

    r3380 r3437  
    1 pkipplib : IPP and CUPS support for Python 
     1ypkipplib : IPP and CUPS support for Python 
    22 
    33$Id$ 
     
    88# the Free Software Foundation, either version 3 of the License, or 
    99# (at your option) any later version. 
    10 #  
     10# 
    1111# This program is distributed in the hope that it will be useful, 
    1212# but WITHOUT ANY WARRANTY; without even the implied warranty of 
    1313# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the 
    1414# GNU General Public License for more details. 
    15 #  
     15# 
    1616# You should have received a copy of the GNU General Public License 
    1717# along with this program.  If not, see <http://www.gnu.org/licenses/>. 
     
    2929and its instance methods. 
    3030 
    31 Finally, a CUPS class can be leveraged to easily deal with CUPS  
     31Finally, a CUPS class can be leveraged to easily deal with CUPS 
    3232print servers. 
    3333 
     
    4242 
    4343        1 - Grab the latest version of this library from : 
    44          
     44 
    4545            http://www.pykota.com/software/pkipplib/ 
    46              
    47         2 - Extract the tarball :     
    48          
     46 
     47        2 - Extract the tarball : 
     48 
    4949            $ tar -zxf pkipplib-x.yy.tar.gz 
    50              
    51         3 - Install the Python module :     
    52          
     50 
     51        3 - Install the Python module : 
     52 
    5353            $ cd pkipplib-x.yy 
    5454            $ python setup.py install 
     
    7878print request 
    7979 
    80 # Access one of the job's attributes directly  
     80# Access one of the job's attributes directly 
    8181print request.job["job-name"] 
    8282--- CUT --- 
     
    119119# Lower level API : 
    120120request = cups.newRequest(pkipplib.IPP_GET_PRINTER_ATTRIBUTES) 
    121 request.operation["printer-uri"] = ("uri",  
     121request.operation["printer-uri"] = ("uri", 
    122122                                    cups.identifierToURI("printers", "HP2100")) 
    123 for attribute in ("printer-uri-supported",                                      
     123for attribute in ("printer-uri-supported", 
    124124                  "printer-type", 
    125125                  "member-uris") : 
    126     # IMPORTANT : here, despite the unusual syntax, we append to               
     126    # IMPORTANT : here, despite the unusual syntax, we append to 
    127127    # the list of requested attributes : 
    128128    request.operation["requested-attributes"] = ("nameWithoutLanguage", attribute) 
    129      
    130 # Sends this request to the CUPS server     
     129 
     130# Sends this request to the CUPS server 
    131131answer = cups.doRequest(request) 
    132132 
     
    140140 
    141141  pkipplib currently includes the following command line tools : 
    142    
     142 
    143143    * pksubscribe : can create or delete IPP subscriptions. 
    144      
     144 
    145145          See pksubscribe --help for details. 
    146          
     146 
    147147          examples : 
    148            
     148 
    149149            $ pksubscribe --cups http://localhost:631 \ 
    150150                          --events printer-added,printer-deleted \ 
    151151                          --recipient mynotifier \ 
    152152                          --duration 0 
    153                            
    154             $ pksubscribe --username root \               
     153 
     154            $ pksubscribe --username root \ 
    155155                          --password HacKMe \ 
    156156                          --delete 34 58 98 
    157                            
     157 
    158158    * samplenotifier : can handle printer-added and printer-deleted 
    159159      notifications and automatically create or remove printers 
    160160      from PyKota's database (just adapt the code for other needs). 
    161        
     161 
    162162      samplenotifier is present in the notifiers/ directory, but 
    163163      won't be installed automatically. You must put it into 
     
    165165 
    166166  In the future more command line tools will be included. 
    167    
     167 
    168168======================================================================= 
    169169 
  • pkipplib/trunk/setup.py

    r45 r3437  
    11#! /usr/bin/env python 
    2 # -*- coding: UTF-8 -*- 
     2# -*- coding: utf-8 -*- 
    33# 
    44# pkipplib : IPP and CUPS support for Python 
     
    99# the Free Software Foundation, either version 3 of the License, or 
    1010# (at your option) any later version. 
    11 #  
     11# 
    1212# This program is distributed in the hope that it will be useful, 
    1313# but WITHOUT ANY WARRANTY; without even the implied warranty of 
    1414# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the 
    1515# GNU General Public License for more details. 
    16 #  
     16# 
    1717# You should have received a copy of the GNU General Public License 
    1818# along with this program.  If not, see <http://www.gnu.org/licenses/>. 
  • pkipplib/trunk/tests/printjob.py

    r46 r3437  
    1 #! /usr/bin/env python 
     1y#! /usr/bin/env python 
    22# -*- coding: ISO-8859-15 -*- 
    33# 
     
    99# the Free Software Foundation, either version 3 of the License, or 
    1010# (at your option) any later version. 
    11 #  
     11# 
    1212# This program is distributed in the hope that it will be useful, 
    1313# but WITHOUT ANY WARRANTY; without even the implied warranty of 
    1414# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the 
    1515# GNU General Public License for more details. 
    16 #  
     16# 
    1717# You should have received a copy of the GNU General Public License 
    1818# along with this program.  If not, see <http://www.gnu.org/licenses/>. 
  • pkipplib/trunk/tests/test.py

    r45 r3437  
    11#! /usr/bin/env python 
    2 # -*- coding: UTF-8 -*- 
     2# -*- coding: utf-8 -*- 
    33# 
    44# pkipplib : IPP and CUPS support for Python 
     
    99# the Free Software Foundation, either version 3 of the License, or 
    1010# (at your option) any later version. 
    11 #  
     11# 
    1212# This program is distributed in the hope that it will be useful, 
    1313# but WITHOUT ANY WARRANTY; without even the implied warranty of 
    1414# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the 
    1515# GNU General Public License for more details. 
    16 #  
     16# 
    1717# You should have received a copy of the GNU General Public License 
    1818# along with this program.  If not, see <http://www.gnu.org/licenses/>. 
     
    2323 
    2424sys.path.insert(0, "../pkipplib") 
    25 import pkipplib         
    26      
     25import pkipplib 
     26 
    2727cups = pkipplib.CUPS() 
    2828answer = cups.createSubscription("ipp://localhost/", ["printer-added", "printer-deleted"],