home *** CD-ROM | disk | FTP | other *** search
/ PC Welt 2006 November (DVD) / PCWELT_11_2006.ISO / casper / filesystem.squashfs / usr / lib / python2.4 / site-packages / UpdateManager / MetaRelease.py < prev    next >
Encoding:
Python Source  |  2006-08-24  |  6.7 KB  |  178 lines

  1. # MetaRelease.py 
  2. #  
  3. #  Copyright (c) 2004,2005 Canonical
  4. #  
  5. #  Author: Michael Vogt <michael.vogt@ubuntu.com>
  6. #  This program is free software; you can redistribute it and/or 
  7. #  modify it under the terms of the GNU General Public License as 
  8. #  published by the Free Software Foundation; either version 2 of the
  9. #  License, or (at your option) any later version.
  10. #  This program is distributed in the hope that it will be useful,
  11. #  but WITHOUT ANY WARRANTY; without even the implied warranty of
  12. #  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
  13. #  GNU General Public License for more details.
  14. #  You should have received a copy of the GNU General Public License
  15. #  along with this program; if not, write to the Free Software
  16. #  Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307
  17. #  USA
  18.  
  19. import pygtk
  20. pygtk.require('2.0')
  21. import gobject
  22. import thread
  23. import urllib2
  24. import os
  25. import string
  26. import apt_pkg
  27. import time
  28. import rfc822
  29. from subprocess import Popen,PIPE
  30.  
  31. class Dist(object):
  32.     def __init__(self, name, version, date, supported):
  33.         self.name = name
  34.         self.version = version
  35.         self.date = date
  36.         self.supported = supported
  37.         self.releaseNotesURI = None
  38.         self.upgradeTool = None
  39.         self.upgradeToolSig = None
  40.  
  41. class MetaRelease(gobject.GObject):
  42.  
  43.     # some constants
  44.     METARELEASE_URI = "http://changelogs.ubuntu.com/meta-release"
  45.     METARELEASE_URI_UNSTABLE = "http://changelogs.ubuntu.com/meta-release-development"
  46.     METARELEASE_FILE = "/var/lib/update-manager/meta-release"
  47.  
  48.     __gsignals__ = { 
  49.         'new_dist_available' : (gobject.SIGNAL_RUN_LAST,
  50.                                 gobject.TYPE_NONE,
  51.                                 (gobject.TYPE_PYOBJECT,)),
  52.         'dist_no_longer_supported' : (gobject.SIGNAL_RUN_LAST,
  53.                                       gobject.TYPE_NONE,
  54.                                       ())
  55.  
  56.         }
  57.  
  58.     def __init__(self, useDevelopmentRelase=False):
  59.         gobject.GObject.__init__(self)
  60.         # check what uri to use
  61.         if useDevelopmentRelase:
  62.             self.METARELEASE_URI = self.METARELEASE_URI_UNSTABLE
  63.         # check if we can access the METARELEASE_FILE
  64.         if not os.access(self.METARELEASE_FILE, os.F_OK|os.W_OK|os.R_OK):
  65.             path = os.path.expanduser("~/.update-manager/")
  66.             if not os.path.exists(path):
  67.                 os.mkdir(path)
  68.             self.METARELEASE_FILE = os.path.join(path,"meta-release")
  69.         self.metarelease_information = None
  70.         self.downloading = True
  71.         # we start the download thread here and we have a timeout
  72.         # in the gtk space to test if the download already finished
  73.         # this is needed because gtk is not thread-safe
  74.         t=thread.start_new_thread(self.download, ())
  75.         gobject.timeout_add(1000,self.check)
  76.         
  77.     def get_dist(self):
  78.         " return the codename of the current runing distro "
  79.         p = Popen(["/bin/lsb_release","-c","-s"],stdout=PIPE)
  80.         res = p.wait()
  81.         if res != 0:
  82.             sys.stderr.write("lsb_release returned exitcode: %i\n" % res)
  83.         dist = string.strip(p.stdout.readline())
  84.         #dist = "breezy"
  85.         return dist
  86.     
  87.     def check(self):
  88.         #print "check"
  89.         # check if we have a metarelease_information file
  90.         if self.metarelease_information != None:
  91.             self.parse()
  92.             # return False makes g_timeout() stop
  93.             return False
  94.         # no information yet, keep runing
  95.         return True
  96.             
  97.     def parse(self):
  98.         #print "parse"
  99.         current_dist_name = self.get_dist()
  100.         current_dist = None
  101.         dists = []
  102.  
  103.         # parse the metarelease_information file
  104.         index_tag = apt_pkg.ParseTagFile(self.metarelease_information)
  105.         step_result = index_tag.Step()
  106.         while step_result:
  107.             if index_tag.Section.has_key("Dist"):
  108.                 name = index_tag.Section["Dist"]
  109.                 #print name
  110.                 rawdate = index_tag.Section["Date"]
  111.                 date = time.mktime(rfc822.parsedate(rawdate))
  112.                 supported = bool(index_tag.Section["Supported"])
  113.                 version = index_tag.Section["Version"]
  114.                 # add the information to a new date object
  115.                 dist = Dist(name, version, date,supported)
  116.                 if index_tag.Section.has_key("ReleaseNotes"):
  117.                     dist.releaseNotesURI = index_tag.Section["ReleaseNotes"]
  118.                 if index_tag.Section.has_key("UpgradeTool"):
  119.                     dist.upgradeTool =  index_tag.Section["UpgradeTool"]
  120.                 if index_tag.Section.has_key("UpgradeToolSignature"):
  121.                     dist.upgradeToolSig =  index_tag.Section["UpgradeToolSignature"]
  122.                 dists.append(dist)
  123.                 if name == current_dist_name:
  124.                     current_dist = dist 
  125.             step_result = index_tag.Step()
  126.  
  127.         # first check if the current runing distro is in the meta-release
  128.         # information. if not, we assume that we run on something not
  129.         # supported and silently return
  130.         if current_dist == None:
  131.             print "current dist not found in meta-release file"
  132.             return False
  133.  
  134.         # then see what we can upgrade to (only upgrade to supported dists)
  135.         upgradable_to = ""
  136.         for dist in dists:
  137.             if dist.date > current_dist.date and dist.supported == True: 
  138.                 upgradable_to = dist
  139.                 #print "new dist: %s" % upgradable_to
  140.                 break
  141.  
  142.         # only warn if unsupported and a new dist is available (because 
  143.         # the development version is also unsupported)
  144.         if upgradable_to != "" and not current_dist.supported:
  145.             self.emit("dist_no_longer_supported",upgradabl_to)
  146.         elif upgradable_to != "":
  147.             self.emit("new_dist_available",upgradable_to)
  148.  
  149.         # parsing done and sucessfully
  150.         return True
  151.  
  152.     # the network thread that tries to fetch the meta-index file
  153.     # can't touch the gui, runs as a thread
  154.     def download(self):
  155.         #print "download"
  156.         lastmodified = 0
  157.         req = urllib2.Request(self.METARELEASE_URI)
  158.         if os.access(self.METARELEASE_FILE, os.W_OK):
  159.             lastmodified = os.stat(self.METARELEASE_FILE).st_mtime
  160.         if lastmodified > 0:
  161.             req.add_header("If-Modified-Since", lastmodified)
  162.         try:
  163.             uri=urllib2.urlopen(req)
  164.             f=open(self.METARELEASE_FILE,"w+")
  165.             for line in uri.readlines():
  166.                 f.write(line)
  167.             f.flush()
  168.             f.seek(0,0)
  169.             self.metarelease_information=f
  170.             uri.close()
  171.         except urllib2.URLError:
  172.             if os.path.exists(self.METARELEASE_FILE):
  173.                 f=open(self.METARELEASE_FILE,"r")
  174.  
  175.