PK˜X–7“×2EGG-INFO/dependency_links.txt PK#S–7“×2EGG-INFO/not-zip-safe PK˜X–7ÕeÕÕ§L§LEGG-INFO/PKG-INFOMetadata-Version: 1.0 Name: TileCache Version: 2.0 Summary: a web map tile caching system Home-page: http://tilecache.org/ Author: MetaCarta Labs Author-email: tilecache@openlayers.org License: BSD Description: =========== tilecache =========== ------------------------- Cache and serve map tiles ------------------------- :Author: labs@metacarta.com :Date: 2007-12-22 :Copyright: (c) 2006-2007 MetaCarta, Inc. Distributed under the BSD license. :Version: 2.0 :Manual section: 8 :Manual group: GIS Utilities DESCRIPTION =========== TileCache is a BSD licensed tile caching mechanism. The goal is to make it easy to set up a WMS or TMS frontend to any backend data services you might be interested in, using a pluggable caching and rendering mechanism. TileCache was developed by MetaCarta Labs and released to the public under a BSD license. The TileCache was designed as a companion to OpenLayers, the BSD licensed web mapping interface. If you are using TileCache with OpenLayers, please read the section of this readme which describes how to do so. For additional help with setting up TileCache for use with OpenLayers, please feel free to stop by #openlayers, on irc.freenode.net, or to send email to tilecache@openlayers.org. INSTALLING TILECACHE ==================== Generally, installing TileCache is as simple as downloading a source distribution and unpacking it. For installation systemwide, you can also use the Python Package Index (aka pypi or Cheeseshop) to install TileCache. Simply type easy_install TileCache. Once this is done, you will need to install the TileCache configuration file. A tool to do this is installed, called tilecache_install_config.py. A full installation likely looks like:: $ sudo easy_install TileCache ... Installed /usr/lib/python2.5/site-packages/TileCache-2.0-py2.5.egg $ sudo tilecache_install_config.py Successfully copied file /usr/lib/python2.5/site-packages/TileCache-2.0-py2.5.egg/TileCache/tilecache.cfg to /etc/tilecache.cfg. TileCache is also available as a Debian package from the TileCache homepage. This Debian package is designed to install on Debian etch releases or later. This Debian package should install on Ubuntu Feisty or Gutsy. RUNNING UNDER CGI ================= * Extract the code to some web directory (e.g. in /var/www). * Edit tilecache.cfg to point the DiskCache to the location you wish to cache tiles, and the layers to point to the map file or WMS server you wish to cache. On Debian, this file is in /etc/tilecache.cfg by default. * Permit CGI execution in the TileCache directory. For example, if TileCache is to be run with Apache, the following must be added in your Apache configuration, where /var/www/tilecache is the directory resulting from the code extraction. On Debian, this is typically /usr/lib/cgi-bin. :: AddHandler cgi-script .cgi Options +ExecCGI * Visit: http://example.com/yourdir/tilecache.cgi?LAYERS=basic&SERVICE=WMS &VERSION=1.1.1&REQUEST=GetMap&SRS=EPSG:4326&BBOX=-180,-90,0,90 &WIDTH=256&HEIGHT=256 * Or visit: http://example.com/yourdir/tilecache.cgi/1.0.0/basic/0/0/0.png * If you see a tile you have set up your configuration correctly. Congrats! Non-standard Python Location ---------------------------- If your Python is not at /usr/bin/python on your system, you will need to change the first line of tilecache.cgi to reference the location of your Python binary. A common example is: :: #!/usr/local/bin/python Under Apache, you might see an error message like: :: [Wed Mar 14 19:55:30 2007] [error] [client 127.0.0.1] (2)No such file or directory: exec of '/www/tilecache.cgi' failed to indicate this problem. You can typically locate where Python is installed on your system via the command which python. Windows users: If you are using Windows, you should change the first line of tilecache.cgi to read: :: #!C:/Python/python.exe -u C:/Python should match the location Python is installed under on your system. In Python 2.5, this location is C:/Python25 by default. RUNNING UNDER MOD_PYTHON ======================== * Extract the code to some web directory (e.g. /var/www). * Edit tilecache.cfg to point the DiskCache to the location you wish to cache tiles, and the layers to point to the map file or WMS server you wish to cache * Add the following to your Apache configuration, under a heading: :: AddHandler python-program .py PythonHandler TileCache.Service PythonOption TileCacheConfig /path/to/tilecache.cfg * An example might look like: :: AddHandler python-program .py PythonHandler TileCache.Service PythonOption TileCacheConfig /var/www/tilecache/tilecache.cfg * In this example, /var/www/tilecache is the directory resulting from the code extraction. If you've installed this from a Debian package, the location of your .cfg file is probably /etc/tilecache.cfg. * Edit tilecache.cfg to point to the location of your 'Layers' directory, as demonstrated inside the default tilecache.cfg. * Visit one of the URLs described above, replacing tilecache.cgi with tilecache.py * If you see a tile you have set up your configuration correctly. Congrats! RUNNING STANDALONE (UNDER WSGI) =============================== TileCache as of version 1.4 comes with a standalone HTTP server which uses the WSGI handler. This implementation depends on *Python Paste*, which can be downloaded from: http://cheeseshop.python.org/pypi/Paste For versions of Python earlier than 2.5, you will also need to install wsgiref: http://cheeseshop.python.org/pypi/wsgiref Once you have all the prerequisites installed, simply run: :: python tilecache_http_server.py This will start a webserver listening on port 8080, after which you should be able to open: :: http://hostname:8080/1.0.0/basic/0/0/0.png to see your first tile. RUNNING UNDER FASTCGI ===================== TileCache as of version 1.4 comes with a fastcgi implementation. In order to use this implementation, you will need to install flup, available from: http://trac.saddi.com/flup This implementation also depends on Python Paste, which can be downloaded from: http://cheeseshop.python.org/pypi/Paste Once you have done this, you can configure your fastcgi server to use tilecache.fcgi. Configuring FastCGI is beyond the scope of this documentation. RUNNING UNDER IIS ================= Installing TileCache for use with IIS requires some additional configuration. * Install Python for Windows * Follow "Using Python Scripts with IIS" to setup Python CGI for IIS. http://support.microsoft.com/kb/276494 * Edit metabase.xml to get correct Security Permissions for IIS 6.0. http://blogs.msdn.com/david.wang/archive/2005/04/20/IIS6-CGI-Web-Service-Extension.aspx * Edit tilecache.cgi to specify your configuration file explicitly: :: svc = Service.load("C:\\TileCache\\tilecache.cfg") When using Tilecache with TMS style requests, you will need to change your IIS configuration to allow PATH_INFO to be delivered to the CGI script. http://support.microsoft.com/kb/q184320/ provides information on this topic. If you do not do this, you will get an error message like: "The requested layer (tilecache.cgi) does not exist." CONFIGURATION ============= TileCache is configured by a config file, defaulting to tilecache.cfg. There are several parameters to control TileCache layers that are applicable to all layers: bbox The bounding box of the Layer. The resolutions array defaults to having resolutions which are equal to the bbox divided by 512 (two standard tiles). debug Whether to send debug output to the error.log. Defaults to "yes", can be set to "no" description Layer description, used in some metadata responses. Default is blank. extension File extension of the layer. Used to request images from WMS servers, as well as when writing cache files. layers A string used to describe the layers. Typically passed directly to the renderer. The WMSLayer sends this in the HTTP request, and the MapServerLayer chooses which layer to render based on this string. If no layer is provided, the layer name is used to fill this property. levels An integer, describing the number of 'zoom levels' or scales to support. Overridden by resolutions, if passed. mapfile The absolute file location of a mapfile. Required for MapServer and Mapnik layers. maxResolution The maximum resolution. If this is set, a resolutions array is automatically calculated up to a number of levels controlled by the 'levels' option. metaTile set to "yes" to turn on metaTiling. This will request larger tiles, and split them up using the Python Imaging library. Defaults to "no". metaBuffer an integer number of pixels to request around the outside of the rendered tile. This is good to combat edge effects in various map renderers. Defaults to 10. metaSize A comma seperated pair of integers, which is used to determine how many tiles should be rendered when using metaTiling. Default is 5,5. resolutions Comma seperate list of resolutions you want the TileCache instance to support. size Comma seperated set of integers, describing the width/height of the tiles. Defaults to 256,256 srs String describing the SRS value. Default is "EPSG:4326" type The type of layer. Options are: WMSLayer, MapnikLayer, MapServerLayer, ImageLayer url URL to use when requesting images from a remote WMS server. Required for WMSLayer. watermarkImage The watermarkImage parameter is assigned on a per-layer basis. This is a fully qualified path to an image you would like to apply to each tile. We recommend you use a watermark image the same size as your tiles. If using the default tile size, you should use a 256x256 image. NOTE: Python Imaging Library DOES NOT support interlaced images. watermarkOpacity The watermarkOpacity parameter is assigned on a per-layer basis. This configures the opacity of the watermark over the tile, it is a floating point number between 0 and 1. Usage is optional and will otherwise default. extent_type Setting this to 'loose' will allow TileCache to generate tiles outside the maximum bounding box. Useful for clients that don't know when to stop asking for tiles. tms_type Setting this to "google" will cause tiles to switch vertical order (that is, following the Google style x/y pattern). USING TILECACHE WITH OPENLAYERS =============================== To run OpenLayers with TileCache the URL passed to the OpenLayers.Layer.WMS constructor must point to the TileCache script, i.e. tilecache.cgi or tilecache.py. As an example see the index.html file included in the TileCache distribution. Note: index.html assumes TileCache is set up under CGI (see above). If you set up TileCache under mod_python you'd need to slighly modify index.html: the URL passed to the OpenLayers.Layer.WMS constructor must point to the mod_python script as opposed to the CGI script, so replace tilecache.cgi with tilecache.py. Similarly, you would need to edit this URL if you were to use TileCache with the standalone HTTP Server or FastCGI. The most important thing to do is to ensure that the OpenLayers Layer has the same resolutions and bounding box as your TileCache layer. You can define the resolutions in OpenLayers via the 'resolutions' option or the 'maxResolution' option on the layer. The maxExtent should be defined to match the bbox parameter of the TileCache layer. If you are using TileCache for overlays, you should set the 'reproject' option on the layer to 'false'. USING TILECACHE WITH MAPSERVER ============================== MapServer has a map level metadata option, labelcache_map_edge_buffer, which is set automatically by TileCache to the metaBuffer plus five when metaTiling is on, if it is not set in the mapfile. If you are using MetaTiling, be aware that MapServer generates interlaced PNG files, which PIL will not read. See http://mapserver.gis.umn.edu/docs/faq/pil_mapscript on how to resolve this. SEEDING YOUR TILECACHE ====================== The tilecache_seed.py utility will seed tiles in a cache automatically. You will need to have TileCache set up in one of the previously described configurations. Usage ----- tilecache_seed.py [ []] Arguments --------- url http://example.com/yourdir/tilecache.cgi? or http://example.com/yourdir/tilecache.py layer same layer name that is in the tilecache.cfg zoom start Zoom level to start the process zoom end Zoom level to end the process bbox The bounding box to seed Seeding by center point and radius ---------------------------------- If called without zoom level arguments, tilecache_seed.py will assume that it needs to read a list of points and radii from standard input, in the form: :: ,, ,, ,, ,, The format of this file is: lon the position(s) to seed longitude lat the position(s) to seed latitude radius the radius around the lon/lat to seed in degrees Examples -------- An example with zoom levels 5 through 12 would be like; :: $ tilecache_seed.py "http://example.com/yourdir/tilecache.cgi?" Zip_Codes 5 12 "-118.12500,31.952162238,-116.015625,34.3071438563" The bbox can be dropped and defaults to world lonlat(-180,-90,180,90): :: $ tilecache_seed.py "http://example.com/yourdir/tilecache.cgi?" Zip_Codes 0 9 In center point/radius mode, the zoom level range is not specifiable from the command-line. An example usage might look like: :: $ tilecache_seed.py "http://example.com/yourdir/tilecache.cgi?" Zip_Codes -118.12500,31.952162238,0.05 -121.46327,32.345345645,0.08 ... the seeding will then commence ... CLEANING YOUR TILECACHE ======================= The tilecache_clean.py utility will remove the least recently accessed tiles from a cache, down to a specified size. Usage ----- tilecache_clean.py [options] Options ------- --version show program's version number and exit -h, --help show this help message and exit -s SIZE, --size=SIZE Maximum cache size, in megabytes. -e ENTRIES, --entries=ENTRIES Maximum cache entries. This limits the amount of memory that will be used to store information about tiles to remove. Notes ----- The --entries option to tilecache_clean.py is optional, and is used to regulate how much memory it uses to do its bookkeeping. The default value of 1 million will hopefully keep RAM utilization under about 100M on a 32-bit x86 Linux machine. If tilecache_clean.py doesn't appear to be keeping your disk cache down to an appropriate size, try upping this value. tilecache_clean.py is designed to be run from a cronjob like so: :: 00 05 * * * /usr/local/bin/tilecache_clean.py -s500 /var/www/tilecache Note that, on non-POSIX operating systems (particularly Windows), tilecache_clean.py measures file sizes, and not disk usage. Because most filesystems use entire file blocks for files smaller than a block, running du -s or similar on your disk cache after a cleaning may still return a total cache size larger than you expect. TROUBLESHOOTING =============== Occasionally, for some reason, when using meta tiles, your server may leave behind lock files. If this happens, there will be files in your cache directory with the extension '.lck'. If you are seeing tiles not render and taking multiple minutes before returning a 500 error, you may be suffering under a stuck lock. Removing all files with extension '.lck' from the cache directory will resolve this problem. SEE ALSO ======== memcached(8) http://tilecache.org/ http://openlayers.org/ http://wiki.osgeo.org/index.php/WMS_Tiling_Client_Recommendation http://wiki.osgeo.org/index.php/Tile_Map_Service_Specification Platform: UNKNOWN PK˜X–7¶5’’EGG-INFO/SOURCES.txtez_setup.py index.html setup.py tilecache.cfg tilecache.cgi tilecache.fcgi tilecache_clean.py tilecache_http_server.py tilecache_install_config.py tilecache_seed.py TileCache/Cache.py TileCache/Client.py TileCache/Layer.py TileCache/Service.py TileCache/Swarm.py TileCache/__init__.py TileCache.egg-info/PKG-INFO TileCache.egg-info/SOURCES.txt TileCache.egg-info/dependency_links.txt TileCache.egg-info/not-zip-safe TileCache.egg-info/top_level.txt TileCache/Caches/Disk.py TileCache/Caches/Memcached.py TileCache/Caches/__init__.py TileCache/Layers/ArcXML.py TileCache/Layers/Image.py TileCache/Layers/MapServer.py TileCache/Layers/Mapnik.py TileCache/Layers/WMS.py TileCache/Layers/__init__.py TileCache/Peer/Twisted.py TileCache/Services/KML.py TileCache/Services/MGMaps.py TileCache/Services/TMS.py TileCache/Services/TileService.py TileCache/Services/WMS.py TileCache/Services/WMTS.py TileCache/Services/WorldWind.py TileCache/Services/__init__.py debian/README.Debian debian/changelog debian/compat debian/control debian/copyright debian/dirs debian/docs debian/manpages debian/rules debian/tilecache.8 debian/tilecache.cfg.5 debian/tilecache_clean.8 debian/tilecache_http_server.8 debian/tilecache_seed.8 debian/watch docs/CHANGELOG.txt docs/CONTRIBUTORS.txt docs/EXAMPLES.txt docs/Example.py docs/LICENSE.txt docs/README.txt tests/HACKING.swarm.txt tests/HACKING.txt tests/Service.txt tests/__init__.py tests/tests.py PK˜X–7»=éG EGG-INFO/top_level.txtTileCache PK˜X–7_¼BwœœEGG-INFO/scripts/tilecache.cgi#!/sw/bin/python2.3 from TileCache import Service, cgiHandler, cfgfiles if __name__ == '__main__': svc = Service.load(*cfgfiles) cgiHandler(svc) PK˜X–7›’óꦦEGG-INFO/scripts/tilecache.fcgi#!/sw/bin/python2.3 from TileCache.Service import wsgiApp if __name__ == '__main__': from flup.server.fcgi_fork import WSGIServer WSGIServer(wsgiApp).run() PK˜X–7§øŽç ç #EGG-INFO/scripts/tilecache_clean.py#!/sw/bin/python2.3 # BSD Licensed, Copyright (c) 2006-2007 MetaCarta, Inc. """This is intended to be run as a command line tool. Use --help to determine arguments to this program. It is a tool to keep a certain directory to a maximum size by removing least recently accessed files from the directory.""" import sys, os, heapq, time from optparse import OptionParser MAX_HEAP_SIZE = 1000000 MAX_CACHE_SIZE = 500 # MB def walk_disk_cache (rootdir, max_entries): """Walk a directory structure, building a heap of up to max_entries.""" heap = [] cache_size = 0 start = time.time() for root, dirs, files in os.walk(rootdir): for file in files: path = os.path.join(root, file) stat = os.stat(path) size = stat.st_size if hasattr(stat, 'st_blocks'): size = stat.st_blocks * stat.st_blksize # strip off rootdir to keep RAM use down path = path[len(rootdir):] heapq.heappush(heap, (stat.st_atime, size, path)) cache_size += size del heap[max_entries:] return heap, cache_size def clean_disk_cache (rootdir, max_size, max_entries): """Remove files from directory until its size is less than max_size (which is megabytes). Up to max_entries will be removed per-run.""" heap, cache_size = walk_disk_cache(rootdir, max_entries) max_size <<= 20 # megabytes print "Cache entries found: %d" % len(heap) removed_files = 0 while heap and cache_size > max_size: atime, size, path = heapq.heappop(heap) cache_size -= size path = rootdir + path try: os.unlink(path) removed_files += 1 except OSError, e: print >>sys.stderr, "Error removing tile %s: %s" % (path, e) print "Removed %d files." % removed_files if __name__ == "__main__": usage = "usage: %prog [options] " parser = OptionParser(usage=usage, version="%prog 1.0") parser.add_option("-s", "--size", action="store", type="int", dest="size", default = MAX_CACHE_SIZE, help="Maximum cache size, in megabytes.") parser.add_option("-e", "--entries", action="store", type="int", dest="entries", default=MAX_HEAP_SIZE, help="""Maximum cache entries. This limits the amount of memory that will be used to store information about tiles to remove.""") (options, args) = parser.parse_args() if not len(args): parser.error("Missing required cache_location argument.") clean_disk_cache(args[0], options.size, options.entries) PK˜X–7âðŸ'')EGG-INFO/scripts/tilecache_http_server.py#!/sw/bin/python2.3 from TileCache.Service import wsgiApp if __name__ == '__main__': from wsgiref import simple_server print "Listening on port 8080" httpd = simple_server.WSGIServer(('',8080), simple_server.WSGIRequestHandler,) httpd.set_app(wsgiApp) httpd.serve_forever() PK˜X–7':rP¿¿,EGG-INFO/scripts/tilecache_install_config.py#!/sw/bin/python2.3 """Script to install a TileCache config from an egg installation.""" import sys from optparse import OptionParser def install(dest): try: f = open(dest, "w") except IOError, E: print "Unable to open destination file %s. Perhaps you need permission to write there?\n(Error was: %s)" % (dest, E) sys.exit(1) try: import pkg_resources filename = pkg_resources.resource_filename("TileCache", "tilecache.cfg") cfg = open(filename, "r") except Exception, E: print "Unable to open source file.\n(Error was: %s)" % (E) sys.exit(1) f.write(cfg.read()) f.close() cfg.close() print "Successfully copied file %s to %s." % (filename, dest) if __name__ == "__main__": parser = OptionParser(usage="""%prog [options] This script is a helper script designed to install the default TileCache configuration when TileCache is installed from an egg.""") parser.add_option('-d', '--dest', dest="dest", help="install to FILE. Default is /etc/tilecache.cfg", default="/etc/tilecache.cfg", metavar="FILE") (options, args) = parser.parse_args() install(options.dest) PK˜X–7>õàõõ"EGG-INFO/scripts/tilecache_seed.py#!/sw/bin/python2.3 # BSD Licensed, Copyright (c) 2006-2007 MetaCarta, Inc. """This is intended to be run as a command line tool. See the accompanying README file or man page for details.""" import TileCache.Client TileCache.Client.main() PKw „7°é=A‹‹TileCache/__init__.py# BSD Licensed, Copyright (c) 2006-2007 MetaCarta, Inc. from Cache import * from Layer import * from Client import * from Service import * PK˜X–73ˆààTileCache/__init__.pyc;ò òøUGc@s dkTdkTdkTdkTdS((s*N(sCachesLayersClientsService(((s8build/bdist.darwin-8.11.1-i386/egg/TileCache/__init__.pys?sPK…7/¡bVVTileCache/Cache.py# BSD Licensed, Copyright (c) 2006-2007 MetaCarta, Inc. import os, sys, time from warnings import warn class Cache (object): def __init__ (self, timeout = 30.0, stale_interval = 300.0, readonly = False, **kwargs): self.stale = float(stale_interval) self.timeout = float(timeout) self.readonly = readonly def lock (self, tile, blocking = True): start_time = time.time() result = self.attemptLock(tile) if result: return True elif not blocking: return False while result is not True: if time.time() - start_time > self.timeout: raise Exception("You appear to have a stuck lock. You may wish to remove the lock named:\n%s" % self.getLockName(tile)) time.sleep(0.25) result = self.attemptLock(tile) return True def getLockName (self, tile): return self.getKey(tile) + ".lck" def getKey (self, tile): raise NotImplementedError() def attemptLock (self, tile): raise NotImplementedError() def unlock (self, tile): raise NotImplementedError() def get (self, tile): raise NotImplementedError() def set (self, tile, data): raise NotImplementedError() def delete(self, tile): raise NotImplementedError() PK˜X–7Ñ:뵩 © TileCache/Cache.pyc;ò u=VGc@sBdkZdkZdkZdklZdefd„ƒYZdS(N(swarnsCachecBsetZdded„Zed„Zd„Zd„Zd„Zd„Z d „Z d „Z d „Z RS( Nf30.0f300.0cKs+t|ƒ|_t|ƒ|_||_dS(N(sfloatsstale_intervalsselfsstalestimeoutsreadonly(sselfstimeoutsstale_intervalsreadonlyskwargs((s5build/bdist.darwin-8.11.1-i386/egg/TileCache/Cache.pys__init__scCsªtiƒ}|i|ƒ}|otSn| otSnxe|tj oWtiƒ||i jot d|i |ƒƒ‚nti dƒ|i|ƒ}q=WtSdS(NsJYou appear to have a stuck lock. You may wish to remove the lock named: %sf0.25( stimes start_timesselfs attemptLockstilesresultsTruesblockingsFalsestimeouts Exceptions getLockNamessleep(sselfstilesblockingsresults start_time((s5build/bdist.darwin-8.11.1-i386/egg/TileCache/Cache.pyslock s   cCs|i|ƒdSdS(Ns.lck(sselfsgetKeystile(sselfstile((s5build/bdist.darwin-8.11.1-i386/egg/TileCache/Cache.pys getLockNamescCs tƒ‚dS(N(sNotImplementedError(sselfstile((s5build/bdist.darwin-8.11.1-i386/egg/TileCache/Cache.pysgetKeyscCs tƒ‚dS(N(sNotImplementedError(sselfstile((s5build/bdist.darwin-8.11.1-i386/egg/TileCache/Cache.pys attemptLockscCs tƒ‚dS(N(sNotImplementedError(sselfstile((s5build/bdist.darwin-8.11.1-i386/egg/TileCache/Cache.pysunlock"scCs tƒ‚dS(N(sNotImplementedError(sselfstile((s5build/bdist.darwin-8.11.1-i386/egg/TileCache/Cache.pysget%scCs tƒ‚dS(N(sNotImplementedError(sselfstilesdata((s5build/bdist.darwin-8.11.1-i386/egg/TileCache/Cache.pysset(scCs tƒ‚dS(N(sNotImplementedError(sselfstile((s5build/bdist.darwin-8.11.1-i386/egg/TileCache/Cache.pysdelete+s( s__name__s __module__sFalses__init__sTrueslocks getLockNamesgetKeys attemptLocksunlocksgetssetsdelete(((s5build/bdist.darwin-8.11.1-i386/egg/TileCache/Cache.pysCaches       (sosssysstimeswarningsswarnsobjectsCache(swarnsCachessysstimesos((s5build/bdist.darwin-8.11.1-i386/egg/TileCache/Cache.pys?s PKw „7—zü¶¶TileCache/Client.py#!/usr/bin/env python # BSD Licensed, Copyright (c) 2006-2007 MetaCarta, Inc. import sys, urllib, urllib2, time, os, math import httplib # setting this to True will exchange more useful error messages # for privacy, hiding URLs and error messages. HIDE_ALL = False class WMS (object): fields = ("bbox", "srs", "width", "height", "format", "layers", "styles") defaultParams = {'version': '1.1.1', 'request': 'GetMap', 'service': 'WMS'} __slots__ = ("base", "params", "client", "data", "response") def __init__ (self, base, params): self.base = base if self.base[-1] not in "?&": if "?" in self.base: self.base += "&" else: self.base += "?" self.params = {} self.client = urllib2.build_opener() for key, val in self.defaultParams.items(): if self.base.lower().rfind("%s=" % key.lower()) == -1: self.params[key] = val for key in self.fields: if params.has_key(key): self.params[key] = params[key] elif self.base.lower().rfind("%s=" % key.lower()) == -1: self.params[key] = "" def url (self): return self.base + urllib.urlencode(self.params) def fetch (self): urlrequest = urllib2.Request(self.url()) # urlrequest.add_header("User-Agent", # "Mozilla/4.0 (compatible; MSIE 6.0; Windows NT 5.1; SV1)" ) response = None while response is None: try: response = self.client.open(urlrequest) data = response.read() # check to make sure that we have an image... msg = response.info() if msg.has_key("Content-Type"): ctype = msg['Content-Type'] if ctype[:5].lower() != 'image': if HIDE_ALL: raise Exception("Did not get image data back. (Adjust HIDE_ALL for more detail.)") else: raise Exception("Did not get image data back. \nURL: %s\nContent-Type Header: %s\nResponse: \n%s" % (self.url(), ctype, data)) except httplib.BadStatusLine: response = None # try again return data, response def setBBox (self, box): self.params["bbox"] = ",".join(map(str, box)) def seed (svc, base, layer, levels = (0, 5), bbox = None): from Layer import Tile if not bbox: bbox = layer.bbox start = time.time() total = 0 for z in range(*levels): bottomleft = layer.getClosestCell(z, bbox[0:2]) topright = layer.getClosestCell(z, bbox[2:4]) print >>sys.stderr, "###### %s, %s" % (bottomleft, topright) zcount = 0 metaSize = layer.getMetaSize(z) ztiles = int(math.ceil(float(topright[1] - bottomleft[1]) / metaSize[0]) * math.ceil(float(topright[0] - bottomleft[0]) / metaSize[1])) for y in range(bottomleft[1], topright[1], metaSize[1]): for x in range(bottomleft[0], topright[0], metaSize[0]): tileStart = time.time() tile = Tile(layer,x,y,z) bounds = tile.bounds() svc.renderTile(tile) total += 1 zcount += 1 box = "(%.4f %.4f %.4f %.4f)" % bounds print "%02d (%06d, %06d) = %s [%.4fs : %.3f/s] %s/%s" \ % (z,x,y, box, time.time() - tileStart, total / (time.time() - start + .0001), zcount, ztiles) def main (): from Service import Service, cfgfiles from Layer import Layer base = sys.argv[1] svc = Service.load(*cfgfiles) layer = svc.layers[sys.argv[2]] if len(sys.argv) == 5: seed(svc, base, layer, map(int, sys.argv[3:])) elif len(sys.argv) == 6: seed(svc, base, layer, map(int, sys.argv[3:5]), map(float, sys.argv[5].split(","))) else: for line in sys.stdin.readlines(): lat, lon, delta = map(float, line.split(",")) bbox = (lon - delta, lat - delta, lon + delta, lat + delta) print "===> %s <===" % (bbox,) seed(svc, base, layer, (5, 17), bbox) if __name__ == '__main__': main() PK˜X–7+[cbggTileCache/Client.pyc;ò òøUGc@s•dkZdkZdkZdkZdkZdkZdkZeZde fd„ƒYZ ddfe d„Z d„Z edjo e ƒndS(NsWMScBs}tZdddddddfZhdd <d d <d d  %s <===i(sServicescfgfilessLayerssyssargvsbasesloadssvcslayersslayerslensseedsmapsintsfloatssplitsstdins readlinesslineslatslonsdeltasbbox( sLayerscfgfilessServiceslonssvcslayersbasesdeltaslatslinesbbox((s6build/bdist.darwin-8.11.1-i386/egg/TileCache/Client.pysmainZs  'F!" s__main__(ssyssurllibsurllib2stimesossmathshttplibsFalsesHIDE_ALLsobjectsWMSsNonesseedsmains__name__( shttplibsWMSsHIDE_ALLsurllib2surllibssyssseedstimesmainsossmath((s6build/bdist.darwin-8.11.1-i386/egg/TileCache/Client.pys?s6 4  PK$B–7KJÜ»£,£,TileCache/Layer.py# BSD Licensed, Copyright (c) 2006-2007 MetaCarta, Inc. import os, sys from warnings import warn from Client import WMS from Service import TileCacheException DEBUG = True class Tile (object): __slots__ = ( "layer", "x", "y", "z", "data" ) def __init__ (self, layer, x, y, z): self.layer = layer self.x = x self.y = y self.z = z self.data = None def size (self): return self.layer.size def bounds (self): res = self.layer.resolutions[self.z] minx = self.layer.bbox[0] + (res * self.x * self.layer.size[0]) miny = self.layer.bbox[1] + (res * self.y * self.layer.size[1]) maxx = self.layer.bbox[0] + (res * (self.x + 1) * self.layer.size[0]) maxy = self.layer.bbox[1] + (res * (self.y + 1) * self.layer.size[1]) return (minx, miny, maxx, maxy) def bbox (self): return ",".join(map(str, self.bounds())) class MetaTile (Tile): def actualSize (self): metaCols, metaRows = self.layer.getMetaSize(self.z) return ( self.layer.size[0] * metaCols, self.layer.size[1] * metaRows ) def size (self): actual = self.actualSize() return ( actual[0] + self.layer.metaBuffer[0] * 2, actual[1] + self.layer.metaBuffer[1] * 2 ) def bounds (self): tilesize = self.actualSize() res = self.layer.resolutions[self.z] buffer = (res * self.layer.metaBuffer[0], res * self.layer.metaBuffer[1]) metaWidth = res * tilesize[0] metaHeight = res * tilesize[1] minx = self.layer.bbox[0] + self.x * metaWidth - buffer[0] miny = self.layer.bbox[1] + self.y * metaHeight - buffer[1] maxx = minx + metaWidth + 2 * buffer[0] maxy = miny + metaHeight + 2 * buffer[1] return (minx, miny, maxx, maxy) class Layer (object): __slots__ = ( "name", "layers", "bbox", "size", "resolutions", "extension", "srs", "cache", "debug", "description", "watermarkimage", "watermarkopacity", "extent_type", "tms_type", "units", "mime_type") def __init__ (self, name, layers = None, bbox = (-180, -90, 180, 90), srs = "EPSG:4326", description = "", maxresolution = None, size = (256, 256), levels = 20, resolutions = None, extension = "png", mime_type = None, cache = None, debug = True, watermarkimage = None, watermarkopacity = 0.2, extent_type = "strict", units = None, tms_type = "" ): self.name = name self.description = description self.layers = layers or name if isinstance(bbox, str): bbox = map(float,bbox.split(",")) self.bbox = bbox if isinstance(size, str): size = map(int,size.split(",")) self.size = size self.units = units self.srs = srs if extension.lower() == 'jpg': extension = 'jpeg' # MIME self.extension = extension.lower() self.mime_type = mime_type or self.format() if isinstance(debug, str): debug = debug.lower() not in ("false", "off", "no", "0") self.cache = cache self.debug = debug self.extent_type = extent_type self.tms_type = tms_type if resolutions: if isinstance(resolutions, str): resolutions = map(float,resolutions.split(",")) self.resolutions = resolutions else: maxRes = None if not maxresolution: width = bbox[2] - bbox[0] height = bbox[3] - bbox[1] if width >= height: aspect = int( float(width) / height + .5 ) # round up maxRes = float(width) / (size[0] * aspect) else: aspect = int( float(height) / width + .5 ) # round up maxRes = float(height) / (size[1] * aspect) else: maxRes = float(maxresolution) self.resolutions = [maxRes / 2 ** i for i in range(int(levels))] self.watermarkimage = watermarkimage self.watermarkopacity = float(watermarkopacity) def getResolution (self, (minx, miny, maxx, maxy)): return max( (maxx - minx) / self.size[0], (maxy - miny) / self.size[1] ) def getLevel (self, res, size = [256, 256]): max_diff = res / max(size[0], size[1]) z = None for i in range(len(self.resolutions)): if abs( self.resolutions[i] - res ) < max_diff: res = self.resolutions[i] z = i break if z is None: raise TileCacheException("can't find resolution index for %f. Available resolutions are: \n%s" % (res, self.resolutions)) return z def getCell (self, (minx, miny, maxx, maxy), exact = True): if exact and self.extent_type == "strict" and not self.contains((minx, miny)): raise TileCacheException("Lower left corner (%f, %f) is outside layer bounds %s. \nTo remove this condition, set extent_type=loose in your configuration." % (minx, miny, self.bbox)) return None res = self.getResolution((minx, miny, maxx, maxy)) x = y = None z = self.getLevel(res, self.size) res = self.resolutions[z] x0 = (minx - self.bbox[0]) / (res * self.size[0]) y0 = (miny - self.bbox[1]) / (res * self.size[1]) x = int(round(x0)) y = int(round(y0)) tilex = ((x * res * self.size[0]) + self.bbox[0]) tiley = ((y * res * self.size[1]) + self.bbox[1]) if exact: if (abs(minx - tilex) / res > 1): raise TileCacheException("Current x value %f is too far from tile corner x %f" % (minx, tilex)) if (abs(miny - tiley) / res > 1): raise TileCacheException("Current y value %f is too far from tile corner y %f" % (miny, tiley)) return (x, y, z) def getClosestCell (self, z, (minx, miny)): res = self.resolutions[z] maxx = minx + self.size[0] * res maxy = miny + self.size[1] * res return self.getCell((minx, miny, maxx, maxy), False) def getTile (self, bbox): coord = self.getCell(bbox) if not coord: return None return Tile(self, *coord) def contains (self, (x, y)): return x >= self.bbox[0] and x <= self.bbox[2] \ and y >= self.bbox[1] and y <= self.bbox[3] def grid (self, z): width = (self.bbox[2] - self.bbox[0]) / (self.resolutions[z] * self.size[0]) height = (self.bbox[3] - self.bbox[1]) / (self.resolutions[z] * self.size[1]) return (width, height) def format (self): return "image/" + self.extension def renderTile (self, tile): # To be implemented by subclasses pass def render (self, tile): return self.renderTile(tile) class MetaLayer (Layer): __slots__ = ('metaTile', 'metaSize', 'metaBuffer') def __init__ (self, name, metatile = "", metasize = (5,5), metabuffer = (10,10), **kwargs): Layer.__init__(self, name, **kwargs) self.metaTile = metatile.lower() in ("true", "yes", "1") if isinstance(metasize, str): metasize = map(int,metasize.split(",")) if isinstance(metabuffer, str): metabuffer = map(int, metabuffer.split(",")) if len(metabuffer) == 1: metabuffer = (metabuffer[0], metabuffer[0]) self.metaSize = metasize self.metaBuffer = metabuffer def getMetaSize (self, z): if not self.metaTile: return (1,1) maxcol, maxrow = self.grid(z) return ( min(self.metaSize[0], int(maxcol + 1)), min(self.metaSize[1], int(maxrow + 1)) ) def getMetaTile (self, tile): x = int(tile.x / self.metaSize[0]) y = int(tile.y / self.metaSize[1]) return MetaTile(self, x, y, tile.z) def renderMetaTile (self, metatile, tile): import StringIO, Image data = self.renderTile(metatile) image = Image.open( StringIO.StringIO(data) ) metaCols, metaRows = self.getMetaSize(metatile.z) metaHeight = metaRows * self.size[1] + 2 * self.metaBuffer[1] for i in range(metaCols): for j in range(metaRows): minx = i * self.size[0] + self.metaBuffer[0] maxx = minx + self.size[0] ### this next calculation is because image origin is (top,left) maxy = metaHeight - (j * self.size[1] + self.metaBuffer[1]) miny = maxy - self.size[1] subimage = image.crop((minx, miny, maxx, maxy)) buffer = StringIO.StringIO() if image.info.has_key('transparency'): subimage.save(buffer, self.extension, transparency=image.info['transparency']) else: subimage.save(buffer, self.extension) buffer.seek(0) subdata = buffer.read() x = metatile.x * self.metaSize[0] + i y = metatile.y * self.metaSize[1] + j subtile = Tile( self, x, y, metatile.z ) if self.watermarkimage: subdata = self.watermark(subdata) self.cache.set( subtile, subdata ) if x == tile.x and y == tile.y: tile.data = subdata return tile.data def render (self, tile): if self.metaTile: metatile = self.getMetaTile(tile) try: self.cache.lock(metatile) image = self.cache.get(tile) if not image: image = self.renderMetaTile(metatile, tile) finally: self.cache.unlock(metatile) return image else: if self.watermarkimage: return self.watermark(self.renderTile(tile)) else: return self.renderTile(tile) def watermark (self, img): import StringIO, Image, ImageEnhance tileImage = Image.open( StringIO.StringIO(img) ) wmark = Image.open(self.watermarkimage) assert self.watermarkopacity >= 0 and self.watermarkopacity <= 1 if wmark.mode != 'RGBA': wmark = wmark.convert('RGBA') else: wmark = wmark.copy() alpha = wmark.split()[3] alpha = ImageEnhance.Brightness(alpha).enhance(self.watermarkopacity) wmark.putalpha(alpha) if tileImage.mode != 'RGBA': tileImage = tileImage.convert('RGBA') watermarkedImage = Image.new('RGBA', tileImage.size, (0,0,0,0)) watermarkedImage.paste(wmark, (0,0)) watermarkedImage = Image.composite(watermarkedImage, tileImage, watermarkedImage) buffer = StringIO.StringIO() if watermarkedImage.info.has_key('transparency'): watermarkedImage.save(buffer, self.extension, transparency=compositeImage.info['transparency']) else: watermarkedImage.save(buffer, self.extension) buffer.seek(0) return buffer.read() PK˜X–7!$SÇÝ;Ý;TileCache/Layer.pyc;ò UmGc@s›dkZdkZdklZdklZdklZeZ de fd„ƒYZ de fd„ƒYZ de fd „ƒYZ d e fd „ƒYZdS( N(swarn(sWMS(sTileCacheExceptionsTilecBsAtZdddddfZd„Zd„Zd„Zd „ZRS( NslayersxsyszsdatacCs1||_||_||_||_t|_dS(N(slayersselfsxsyszsNonesdata(sselfslayersxsysz((s5build/bdist.darwin-8.11.1-i386/egg/TileCache/Layer.pys__init__ s     cCs|iiSdS(N(sselfslayerssize(sself((s5build/bdist.darwin-8.11.1-i386/egg/TileCache/Layer.pyssizescCsÓ|ii|i}|iid||i|iid}|iid||i |iid}|iid||id|iid}|iid||i d|iid}||||fSdS(Nii( sselfslayers resolutionsszsressbboxsxssizesminxsysminysmaxxsmaxy(sselfsmaxxsmaxysressminxsminy((s5build/bdist.darwin-8.11.1-i386/egg/TileCache/Layer.pysboundss ))--cCs ditt|iƒƒƒSdS(Ns,(sjoinsmapsstrsselfsbounds(sself((s5build/bdist.darwin-8.11.1-i386/egg/TileCache/Layer.pysbboxs(s__name__s __module__s __slots__s__init__ssizesboundssbbox(((s5build/bdist.darwin-8.11.1-i386/egg/TileCache/Layer.pysTile s    sMetaTilecBs#tZd„Zd„Zd„ZRS(NcCsE|ii|iƒ\}}|iid||iid|fSdS(Nii(sselfslayers getMetaSizeszsmetaColssmetaRowsssize(sselfsmetaRowssmetaCols((s5build/bdist.darwin-8.11.1-i386/egg/TileCache/Layer.pys actualSize!scCsF|iƒ}|d|iidd|d|iiddfSdS(Niii(sselfs actualSizesactualslayers metaBuffer(sselfsactual((s5build/bdist.darwin-8.11.1-i386/egg/TileCache/Layer.pyssize&s c Csé|iƒ}|ii|i}||iid||iidf}||d}||d} |ii d|i ||d}|ii d|i| |d}||d|d}|| d|d}||||fSdS(Niii(sselfs actualSizestilesizeslayers resolutionsszsress metaBuffersbuffers metaWidths metaHeightsbboxsxsminxsysminysmaxxsmaxy( sselfsmaxxsmaxystilesizesbuffersress metaWidthsminxsminys metaHeight((s5build/bdist.darwin-8.11.1-i386/egg/TileCache/Layer.pysbounds+s (##(s__name__s __module__s actualSizessizesbounds(((s5build/bdist.darwin-8.11.1-i386/egg/TileCache/Layer.pysMetaTile s  sLayercBsòtZddddddddd d d d d dddfZeddddfddeddfdedeeeeddedd„Zd„Zddgd„Zed„Zd „Z d!„Z d"„Z d#„Z d$„Z d%„Zd&„ZRS('Nsnameslayerssbboxssizes resolutionss extensionssrsscachesdebugs descriptionswatermarkimageswatermarkopacitys extent_typestms_typesunitss mime_typeiLÿÿÿi¦ÿÿÿi´iZs EPSG:4326siispngf0.20000000000000001sstrictcCs‡||_||_|p||_t|tƒott|i dƒƒ}n||_t|tƒott |i dƒƒ}n||_ ||_ ||_ | iƒdjo d} n| iƒ|_| p |iƒ|_t| tƒo"| iƒddddfj} n| |_| |_||_||_| o9t| tƒott| i dƒƒ} n| |_nöt}| o|d|d }|d |d }||jo6t t|ƒ|d ƒ}t|ƒ|d |}q-t t|ƒ|d ƒ}t|ƒ|d |}n t|ƒ}gi}tt |ƒƒD]}||d|ƒqG~|_||_"t|ƒ|_#dS( Ns,sjpgsjpegsfalsesoffsnos0iiiif0.5($snamesselfs descriptionslayerss isinstancesbboxsstrsmapsfloatssplitssizesintsunitsssrss extensionslowers mime_typesformatsdebugscaches extent_typestms_types resolutionssNonesmaxRess maxresolutionswidthsheightsaspectsappends_[1]srangeslevelssiswatermarkimageswatermarkopacity(sselfsnameslayerssbboxssrss descriptions maxresolutionssizeslevelss resolutionss extensions mime_typescachesdebugswatermarkimageswatermarkopacitys extent_typesunitsstms_typesmaxRessheightsaspectswidthsis_[1]((s5build/bdist.darwin-8.11.1-i386/egg/TileCache/Layer.pys__init__>sL       "       > cCsA|\}}}}t|||id|||idƒSdS(Nii(sminxsminysmaxxsmaxysmaxsselfssize(sselfs.2sminxsminysmaxxsmaxy((s5build/bdist.darwin-8.11.1-i386/egg/TileCache/Layer.pys getResolutionkscCs©|t|d|dƒ}t}xStt|i ƒƒD]<}t |i ||ƒ|jo|i |}|}Pq7q7W|tjot d||i fƒ‚n|SdS(NiisBcan't find resolution index for %f. Available resolutions are: %s( sressmaxssizesmax_diffsNoneszsrangeslensselfs resolutionssisabssTileCacheException(sselfsresssizesismax_diffsz((s5build/bdist.darwin-8.11.1-i386/egg/TileCache/Layer.pysgetLevelos   cCsÕ|\}}}}|o$|idjo|i||fƒ o$td|||i fƒ‚t Sn|i ||||fƒ}t } } |i||iƒ} |i| }||i d||id}||i d||id} tt|ƒƒ} tt| ƒƒ} | ||id|i d} | ||id|i d}|ont|| ƒ|djotd|| fƒ‚nt||ƒ|djotd||fƒ‚qÄn| | | fSdS(Nsstricts~Lower left corner (%f, %f) is outside layer bounds %s. To remove this condition, set extent_type=loose in your configuration.iis3Current x value %f is too far from tile corner x %fs3Current y value %f is too far from tile corner y %f(sminxsminysmaxxsmaxysexactsselfs extent_typescontainssTileCacheExceptionsbboxsNones getResolutionsressxsysgetLevelssizeszs resolutionssx0sy0sintsroundstilexstileysabs(sselfs.2sexactsminxsminysmaxxsmaxystileysresstilexsy0sysxszsx0((s5build/bdist.darwin-8.11.1-i386/egg/TileCache/Layer.pysgetCell{s&.      cCsc|\}}|i|}||id|}||id|}|i ||||ft ƒSdS(Nii( sminxsminysselfs resolutionsszsresssizesmaxxsmaxysgetCellsFalse(sselfszs.4sminxsminysmaxxsmaxysres((s5build/bdist.darwin-8.11.1-i386/egg/TileCache/Layer.pysgetClosestCell˜s  cCs0|i|ƒ}| otSnt||ŒSdS(N(sselfsgetCellsbboxscoordsNonesTile(sselfsbboxscoord((s5build/bdist.darwin-8.11.1-i386/egg/TileCache/Layer.pysgetTiležscCs]|\}}||idjo9||idjo%||idjo||idjSdS(Niiii(sxsysselfsbbox(sselfs.2sxsy((s5build/bdist.darwin-8.11.1-i386/egg/TileCache/Layer.pyscontains£s cCsj|id|id|i||id}|id|id|i||id}||fSdS(Niiii(sselfsbboxs resolutionsszssizeswidthsheight(sselfszswidthsheight((s5build/bdist.darwin-8.11.1-i386/egg/TileCache/Layer.pysgrid§s..cCsd|iSdS(Nsimage/(sselfs extension(sself((s5build/bdist.darwin-8.11.1-i386/egg/TileCache/Layer.pysformat¬scCsdS(N((sselfstile((s5build/bdist.darwin-8.11.1-i386/egg/TileCache/Layer.pys renderTile¯scCs|i|ƒSdS(N(sselfs renderTilestile(sselfstile((s5build/bdist.darwin-8.11.1-i386/egg/TileCache/Layer.pysrender³s(s__name__s __module__s __slots__sNonesTrues__init__s getResolutionsgetLevelsgetCellsgetClosestCellsgetTilescontainssgridsformats renderTilesrender(((s5build/bdist.darwin-8.11.1-i386/egg/TileCache/Layer.pysLayer7s6N-        s MetaLayercBsbtZdddfZdddfddfd„Zd„Zd „Zd „Zd „Zd „ZRS( NsmetaTilesmetaSizes metaBuffersii cKsÊti||||iƒdddfj|_t|t ƒot t |i dƒƒ}nt|t ƒoGt t |i dƒƒ}t|ƒdjo|d|df}q´n||_||_dS(Nstruesyess1s,ii(sLayers__init__sselfsnameskwargssmetatileslowersmetaTiles isinstancesmetasizesstrsmapsintssplits metabufferslensmetaSizes metaBuffer(sselfsnamesmetatilesmetasizes metabufferskwargs((s5build/bdist.darwin-8.11.1-i386/egg/TileCache/Layer.pys__init__¸s cCsp|i oddfSn|i|ƒ\}}t|idt|dƒƒt|idt|dƒƒfSdS(Nii( sselfsmetaTilesgridszsmaxcolsmaxrowsminsmetaSizesint(sselfszsmaxcolsmaxrow((s5build/bdist.darwin-8.11.1-i386/egg/TileCache/Layer.pys getMetaSizeÅs cCsNt|i|idƒ}t|i|idƒ}t||||iƒSdS(Nii(sintstilesxsselfsmetaSizesysMetaTilesz(sselfstilesysx((s5build/bdist.darwin-8.11.1-i386/egg/TileCache/Layer.pys getMetaTileËscCs7dk}dk}|i|ƒ}|i|i|ƒƒ}|i|i ƒ\}}||i dd|i d} x¸t|ƒD]ª}x¡t|ƒD]“}||i d|i d}||i d}| ||i d|i d}||i d}|i||||fƒ} |iƒ} |iidƒo$| i| |id|idƒn| i| |iƒ| idƒ| iƒ} |i |i!d|}|i"|i!d|}t#||||i ƒ} |i%o|i&| ƒ} n|i'i(| | ƒ||i jo ||i"jo | |_q‘q‘Wq~W|iSdS(Niiis transparency(*sStringIOsImagesselfs renderTilesmetatilesdatasopensimages getMetaSizeszsmetaColssmetaRowsssizes metaBuffers metaHeightsrangesisjsminxsmaxxsmaxysminyscropssubimagesbuffersinfoshas_keyssaves extensionsseeksreadssubdatasxsmetaSizesysTilessubtileswatermarkimages watermarkscachessetstile(sselfsmetatilestilesimagesminxsminysmetaRowssmaxxsmaxyssubimagessubdatassubtiles metaHeightsbuffersdatasStringIOsismetaColssjsysxsImage((s5build/bdist.darwin-8.11.1-i386/egg/TileCache/Layer.pysrenderMetaTileÐs:     $    cCs®|ioo|i|ƒ}zD|ii|ƒ|ii|ƒ}| o|i ||ƒ}nWd|ii |ƒX|Sn2|i o|i |i |ƒƒSn|i |ƒSdS(N(sselfsmetaTiles getMetaTilestilesmetatilescacheslocksgetsimagesrenderMetaTilesunlockswatermarkimages watermarks renderTile(sselfstilesmetatilesimage((s5build/bdist.darwin-8.11.1-i386/egg/TileCache/Layer.pysrenderòs  c Cs¶dk}dk} dk}| i|i|ƒƒ}| i|iƒ}|i djo |i djpt ‚|i djo|i dƒ}n |i ƒ}|iƒd}|i|ƒi|i ƒ}|i|ƒ|i djo|i dƒ}n| id|iddddfƒ}|i|ddfƒ| i|||ƒ}|iƒ}|iidƒo$|i||idtidƒn|i||iƒ|idƒ|iƒSdS(NiisRGBAis transparency( sStringIOsImages ImageEnhancesopensimgs tileImagesselfswatermarkimageswmarkswatermarkopacitysAssertionErrorsmodesconvertscopyssplitsalphas BrightnesssenhancesputalphasnewssizeswatermarkedImagespastes compositesbuffersinfoshas_keyssaves extensionscompositeImagesseeksread( sselfsimgswmarks ImageEnhancesbuffersStringIOswatermarkedImages tileImagesalphasImage((s5build/bdist.darwin-8.11.1-i386/egg/TileCache/Layer.pys watermarks*'  $ $ ( s__name__s __module__s __slots__s__init__s getMetaSizes getMetaTilesrenderMetaTilesrenders watermark(((s5build/bdist.darwin-8.11.1-i386/egg/TileCache/Layer.pys MetaLayer¶s   " (sosssysswarningsswarnsClientsWMSsServicesTileCacheExceptionsTruesDEBUGsobjectsTilesMetaTilesLayers MetaLayer( swarnsLayersMetaTilesWMSssyssTilesDEBUGs MetaLayersossTileCacheException((s5build/bdist.darwin-8.11.1-i386/egg/TileCache/Layer.pys?s   PK9ª’7 j}û¥.¥.TileCache/Service.py#!/usr/bin/python # BSD Licensed, Copyright (c) 2006-2007 MetaCarta, Inc. class TileCacheException(Exception): pass import sys, cgi, time, os, traceback, ConfigParser import Cache, Caches import Layer, Layers # Windows doesn't always do the 'working directory' check correctly. if sys.platform == 'win32': workingdir = os.path.abspath(os.path.join(os.getcwd(), os.path.dirname(sys.argv[0]))) cfgfiles = (os.path.join(workingdir, "tilecache.cfg"), os.path.join(workingdir,"..","tilecache.cfg")) else: cfgfiles = ("/etc/tilecache.cfg", os.path.join("..", "tilecache.cfg"), "tilecache.cfg") class Capabilities (object): def __init__ (self, format, data): self.format = format self.data = data class Request (object): def __init__ (self, service): self.service = service def getLayer(self, layername): try: return self.service.layers[layername] except: raise TileCacheException("The requested layer (%s) does not exist. Available layers are: \n * %s" % (layername, "\n * ".join(self.service.layers.keys()))) def import_module(name): """Helper module to import any module based on a name, and return the module.""" mod = __import__(name) components = name.split('.') for comp in components[1:]: mod = getattr(mod, comp) return mod class Service (object): __slots__ = ("layers", "cache", "metadata", "tilecache_options") def __init__ (self, cache, layers, metadata = {}): self.cache = cache self.layers = layers self.metadata = metadata def _loadFromSection (cls, config, section, module, **objargs): type = config.get(section, "type") for opt in config.options(section): if opt not in ["type", "module"]: objargs[opt] = config.get(section, opt) object_module = None if config.has_option(section, "module"): object_module = import_module(config.get(section, "module")) else: if module is Layer: type = type.replace("Layer", "") object_module = import_module("TileCache.Layers.%s" % type) else: type = type.replace("Cache", "") object_module = import_module("TileCache.Caches.%s" % type) if object_module == None: raise TileCacheException("Attempt to load %s failed." % type) section_object = getattr(object_module, type) if module is Layer: return section_object(section, **objargs) else: return section_object(**objargs) loadFromSection = classmethod(_loadFromSection) def _load (cls, *files): config = ConfigParser.ConfigParser() config.read(files) metadata = {} if config.has_section("metadata"): for key in config.options("metadata"): metadata[key] = config.get("metadata", key) if config.has_section("tilecache_options"): if 'path' in config.options("tilecache_options"): for path in config.get("tilecache_options", "path").split(","): sys.path.insert(0, path) cache = cls.loadFromSection(config, "cache", Cache) layers = {} for section in config.sections(): if section in cls.__slots__: continue layers[section] = cls.loadFromSection( config, section, Layer, cache = cache) return cls(cache, layers, metadata) load = classmethod(_load) def renderTile (self, tile, force = False): from warnings import warn start = time.time() # do more cache checking here: SRS, width, height, layers layer = tile.layer image = None if not force: image = self.cache.get(tile) if not image: data = layer.render(tile) if (data): image = self.cache.set(tile, data) else: raise Exception("Zero length data returned from layer.") if layer.debug: sys.stderr.write( "Cache miss: %s, Tile: x: %s, y: %s, z: %s, time: %s\n" % ( tile.bbox(), tile.x, tile.y, tile.z, (time.time() - start)) ) else: if layer.debug: sys.stderr.write( "Cache hit: %s, Tile: x: %s, y: %s, z: %s, time: %s, debug: %s\n" % ( tile.bbox(), tile.x, tile.y, tile.z, (time.time() - start), layer.debug) ) return (layer.mime_type, image) def expireTile (self, tile): bbox = tile.bounds() layer = tile.layer for z in range(len(layer.resolutions)): bottomleft = layer.getClosestCell(z, bbox[0:2]) topright = layer.getClosestCell(z, bbox[2:4]) for y in range(bottomleft[1], topright[1] + 1): for x in range(bottomleft[0], topright[0] + 1): coverage = Tile(layer,x,y,z) self.cache.delete(coverage) def dispatchRequest (self, params, path_info="/", req_method="GET", host="http://example.com/"): if path_info.split(".")[-1] == "kml": from TileCache.Services.KML import KML return KML(self).parse(params, path_info, host) raise TileCacheException("What, you think we do KML?") if params.has_key("scale") or params.has_key("SCALE"): from TileCache.Services.WMTS import WMTS tile = WMTS(self).parse(params, path_info, host) elif params.has_key("service") or params.has_key("SERVICE") or \ params.has_key("REQUEST") and params['REQUEST'] == "GetMap" or \ params.has_key("request") and params['request'] == "GetMap": from TileCache.Services.WMS import WMS tile = WMS(self).parse(params, path_info, host) elif params.has_key("L") or params.has_key("l") or \ params.has_key("request") and params['request'] == "metadata": from TileCache.Services.WorldWind import WorldWind tile = WorldWind(self).parse(params, path_info, host) elif params.has_key("interface"): from TileCache.Services.TileService import TileService tile = TileService(self).parse(params, path_info, host) elif params.has_key("v") and \ (params['v'] == "mgm" or params['v'] == "mgmaps"): from TileCache.Services.MGMaps import MGMaps tile = MGMaps(self).parse(params, path_info, host) else: from TileCache.Services.TMS import TMS tile = TMS(self).parse(params, path_info, host) if isinstance(tile, Layer.Tile): if req_method == 'DELETE': self.expireTile(tile) return ('text/plain', 'OK') else: return self.renderTile(tile, params.has_key('FORCE')) else: return (tile.format, tile.data) def modPythonHandler (apacheReq, service): from mod_python import apache, util try: if apacheReq.headers_in.has_key("X-Forwarded-Host"): host = "http://" + apacheReq.headers_in["X-Forwarded-Host"] else: host = "http://" + apacheReq.headers_in["Host"] host += apacheReq.uri[:-len(apacheReq.path_info)] format, image = service.dispatchRequest( util.FieldStorage(apacheReq), apacheReq.path_info, apacheReq.method, host ) apacheReq.content_type = format apacheReq.send_http_header() apacheReq.write(image) except Layer.TileCacheException, E: apacheReq.content_type = "text/plain" apacheReq.status = apache.HTTP_NOT_FOUND apacheReq.send_http_header() apacheReq.write("An error occurred: %s\n" % (str(E))) except Exception, E: apacheReq.content_type = "text/plain" apacheReq.status = apache.HTTP_INTERNAL_SERVER_ERROR apacheReq.send_http_header() apacheReq.write("An error occurred: %s\n%s\n" % ( str(E), "".join(traceback.format_tb(sys.exc_traceback)))) return apache.OK def wsgiHandler (environ, start_response, service): from paste.request import parse_formvars try: path_info = host = "" if "PATH_INFO" in environ: path_info = environ["PATH_INFO"] if "HTTP_X_FORWARDED_HOST" in environ: host = "http://" + environ["HTTP_X_FORWARDED_HOST"] elif "HTTP_HOST" in environ: host = "http://" + environ["HTTP_HOST"] host += environ["SCRIPT_NAME"] req_method = environ["REQUEST_METHOD"] fields = parse_formvars(environ) format, image = service.dispatchRequest( fields, path_info, req_method, host ) start_response("200 OK", [('Content-Type',format)]) return [image] except TileCacheException, E: start_response("404 Tile Not Found", [('Content-Type','text/plain')]) return ["An error occurred: %s" % (str(E))] except Exception, E: start_response("500 Internal Server Error", [('Content-Type','text/plain')]) return ["An error occurred: %s\n%s\n" % ( str(E), "".join(traceback.format_tb(sys.exc_traceback)))] def cgiHandler (service): try: params = {} input = cgi.FieldStorage() for key in input.keys(): params[key] = input[key].value path_info = host = "" if "PATH_INFO" in os.environ: path_info = os.environ["PATH_INFO"] if "HTTP_X_FORWARDED_HOST" in os.environ: host = "http://" + os.environ["HTTP_X_FORWARDED_HOST"] elif "HTTP_HOST" in os.environ: host = "http://" + os.environ["HTTP_HOST"] host += os.environ["SCRIPT_NAME"] req_method = os.environ["REQUEST_METHOD"] format, image = service.dispatchRequest( params, path_info, req_method, host ) print "Content-type: %s\n" % format if sys.platform == "win32": binaryPrint(image) else: print image except TileCacheException, E: print "Cache-Control: max-age=10, must-revalidate" # make the client reload print "Content-type: text/plain\n" print "An error occurred: %s\n" % (str(E)) except Exception, E: print "Cache-Control: max-age=10, must-revalidate" # make the client reload print "Content-type: text/plain\n" print "An error occurred: %s\n%s\n" % ( str(E), "".join(traceback.format_tb(sys.exc_traceback))) theService = None def handler (apacheReq): global theService options = apacheReq.get_options() cfgs = cfgfiles if options.has_key("TileCacheConfig"): cfgs = (options["TileCacheConfig"],) + cfgs if not theService: theService = Service.load(*cfgs) return modPythonHandler(apacheReq, theService) def wsgiApp (environ, start_response): global theService cfgs = cfgfiles if not theService: theService = Service.load(*cfgs) return wsgiHandler(environ, start_response, theService) def binaryPrint(binary_data): """This function is designed to work around the fact that Python in Windows does not handle binary output correctly. This function will set the output to binary, and then write to stdout directly rather than using print.""" try: import msvcrt msvcrt.setmode(sys.__stdout__.fileno(), os.O_BINARY) except: pass sys.stdout.write(binary_data) if __name__ == '__main__': svc = Service.load(*cfgfiles) cgiHandler(svc) PK˜X–7/·)™P9P9TileCache/Service.pyc;ò OhGc@s¾defd„ƒYZdkZdkZdkZdkZdkZdkZdkZdk Z dk Z dk Z ei djokei iei ieiƒei ieidƒƒƒZei iedƒei ieddƒfZndei iddƒdfZdefd „ƒYZd efd „ƒYZd „Zd efd„ƒYZd„Zd„Zd„Zead„Zd„Z d„Z!e"djoei#eŒZ$ee$ƒndS(sTileCacheExceptioncBstZRS(N(s__name__s __module__(((s7build/bdist.darwin-8.11.1-i386/egg/TileCache/Service.pysTileCacheExceptionsNswin32is tilecache.cfgs..s/etc/tilecache.cfgs CapabilitiescBstZd„ZRS(NcCs||_||_dS(N(sformatsselfsdata(sselfsformatsdata((s7build/bdist.darwin-8.11.1-i386/egg/TileCache/Service.pys__init__s (s__name__s __module__s__init__(((s7build/bdist.darwin-8.11.1-i386/egg/TileCache/Service.pys CapabilitiesssRequestcBstZd„Zd„ZRS(NcCs ||_dS(N(sservicesself(sselfsservice((s7build/bdist.darwin-8.11.1-i386/egg/TileCache/Service.pys__init__scCsKy|ii|SWn2td|di|iiiƒƒfƒ‚nXdS(NsEThe requested layer (%s) does not exist. Available layers are: * %ss * (sselfsserviceslayerss layernamesTileCacheExceptionsjoinskeys(sselfs layername((s7build/bdist.darwin-8.11.1-i386/egg/TileCache/Service.pysgetLayers(s__name__s __module__s__init__sgetLayer(((s7build/bdist.darwin-8.11.1-i386/egg/TileCache/Service.pysRequests cCsGt|ƒ}|idƒ}x!|dD]}t||ƒ}q&W|SdS(sJHelper module to import any module based on a name, and return the module.s.iN(s __import__snamesmodssplits componentsscompsgetattr(snames componentsscompsmod((s7build/bdist.darwin-8.11.1-i386/egg/TileCache/Service.pys import_module!s  sServicecBswtZddddfZhd„Zd„ZeeƒZd„ZeeƒZe d„Z d „Z d d d d „Z RS(Nslayersscachesmetadatastilecache_optionscCs||_||_||_dS(N(scachesselfslayerssmetadata(sselfscacheslayerssmetadata((s7build/bdist.darwin-8.11.1-i386/egg/TileCache/Service.pys__init__,s  c Ks?|i|dƒ}xD|i|ƒD]3}|ddgjo|i||ƒ||Cache hit: %s, Tile: x: %s, y: %s, z: %s, time: %s, debug: %s (swarningsswarnstimesstartstileslayersNonesimagesforcesselfscachesgetsrendersdatassets Exceptionsdebugssyssstderrswritesbboxsxsyszs mime_type(sselfstilesforceslayerswarnsstartsdatasimage((s7build/bdist.darwin-8.11.1-i386/egg/TileCache/Service.pys renderTilegs      D Fc CsÜ|iƒ}|i}xÀtt|iƒƒD]©} |i| |dd!ƒ}|i| |dd!ƒ}xnt|d|ddƒD]Q}xHt|d|ddƒD]+}t |||| ƒ}|ii|ƒq¡WqWq+WdS(Niiii(stilesboundssbboxslayersrangeslens resolutionsszsgetClosestCells bottomleftstoprightsysxsTilescoveragesselfscachesdelete( sselfstileslayers bottomleftstoprightsysbboxscoveragesxsz((s7build/bdist.darwin-8.11.1-i386/egg/TileCache/Service.pys expireTile€s  s/sGETshttp://example.com/c CsÅ|idƒddjo6dkl}||ƒi|||ƒStdƒ‚n|i dƒp |i dƒo,dk l } | |ƒi|||ƒ} n¾|i d ƒpO|i d ƒp?|i d ƒo|d d jp|i d ƒo|d d jo,dk l}||ƒi|||ƒ} n0|i dƒp.|i dƒp|i d ƒo|d djo,dkl}||ƒi|||ƒ} nÃ|i dƒo,dkl} | |ƒi|||ƒ} n‡|i dƒo|ddjp|ddjo,dkl}||ƒi|||ƒ} n)dkl} | |ƒi|||ƒ} t| tiƒoE|djo|i| ƒddfSqÁ|i| |i dƒƒSn| i| ifSdS(Ns.iÿÿÿÿskml(sKMLsWhat, you think we do KML?sscalesSCALE(sWMTSsservicesSERVICEsREQUESTsGetMapsrequest(sWMSsLslsmetadata(s WorldWinds interface(s TileServicesvsmgmsmgmaps(sMGMaps(sTMSsDELETEs text/plainsOKsFORCE(s path_infossplitsTileCache.Services.KMLsKMLsselfsparsesparamsshostsTileCacheExceptionshas_keysTileCache.Services.WMTSsWMTSstilesTileCache.Services.WMSsWMSsTileCache.Services.WorldWinds WorldWindsTileCache.Services.TileServices TileServicesTileCache.Services.MGMapssMGMapssTileCache.Services.TMSsTMSs isinstancesLayersTiles req_methods expireTiles renderTilesformatsdata( sselfsparamss path_infos req_methodshostsMGMapss WorldWindsWMSsKMLsWMTSs TileServicestilesTMS((s7build/bdist.darwin-8.11.1-i386/egg/TileCache/Service.pysdispatchRequest‹s6   b A  2    ( s__name__s __module__s __slots__s__init__s_loadFromSections classmethodsloadFromSections_loadsloadsFalses renderTiles expireTilesdispatchRequest(((s7build/bdist.darwin-8.11.1-i386/egg/TileCache/Service.pysService)s       cCsydkl}l}y¥|iidƒod|id}nd|id}||it|i ƒ 7}|i |i |ƒ|i |i |ƒ\}}||_|iƒ|i|ƒWn³tij o?}d|_|i|_|iƒ|idt|ƒƒngtj oZ}d|_|i|_|iƒ|idt|ƒdititiƒƒfƒnX|i SdS( N(sapachesutilsX-Forwarded-Hostshttp://sHosts text/plainsAn error occurred: %s sAn error occurred: %s %s s(!s mod_pythonsapachesutils apacheReqs headers_inshas_keyshostsurislens path_infosservicesdispatchRequests FieldStoragesmethodsformatsimages content_typessend_http_headerswritesLayersTileCacheExceptionsEsHTTP_NOT_FOUNDsstatussstrs ExceptionsHTTP_INTERNAL_SERVER_ERRORsjoins tracebacks format_tbssyss exc_tracebacksOK(s apacheReqsservicesEsformatsimagesutilshostsapache((s7build/bdist.darwin-8.11.1-i386/egg/TileCache/Service.pysmodPythonHandler±s0        7c Csldkl} yÆd}}d|jo|d}nd|jod|d}n d|jod|d}n||d7}|d} | |ƒ}|i||| |ƒ\}}|d d |fgƒ|gSWn’t j o0}|d d d fgƒd t|ƒgSnXtj oK}|dd d fgƒdt|ƒdititiƒƒfgSnXdS(N(sparse_formvarsss PATH_INFOsHTTP_X_FORWARDED_HOSTshttp://s HTTP_HOSTs SCRIPT_NAMEsREQUEST_METHODs200 OKs Content-Types404 Tile Not Founds text/plainsAn error occurred: %ss500 Internal Server ErrorsAn error occurred: %s %s (s paste.requestsparse_formvarss path_infoshostsenvirons req_methodsfieldssservicesdispatchRequestsformatsimagesstart_responsesTileCacheExceptionsEsstrs Exceptionsjoins tracebacks format_tbssyss exc_traceback( senvironsstart_responsesservicesEsformatsfieldssimageshosts path_infos req_methodsparse_formvars((s7build/bdist.darwin-8.11.1-i386/egg/TileCache/Service.pys wsgiHandlerÏs*        c Cs˜yh}tiƒ}x%|iƒD]}||i||7sisfreeze_(sfilters enumeratesselfstypessmsgtypesnamesstructspacksheaderskeysseq_idsmsgtxtsgetattrstypesdispatch(sselfsnamesdispatchsmsgtypesmsgtxt((sselfs5build/bdist.darwin-8.11.1-i386/egg/TileCache/Swarm.pysfreeze6s   cCsdSdS(Ns((sself((s5build/bdist.darwin-8.11.1-i386/egg/TileCache/Swarm.pys freeze_PING?scCstid|iƒSdS(Ns!L(sstructspacksselfsping_id(sself((s5build/bdist.darwin-8.11.1-i386/egg/TileCache/Swarm.pys freeze_PONGBscCs8|i}ti|i|ii|i|i|i ƒSdS(N( sselfstilesstructspackstilespecslayersnameszsxsy(sselfstile((s5build/bdist.darwin-8.11.1-i386/egg/TileCache/Swarm.pys freeze_GETEs  cCs|iƒ|iiSdS(N(sselfs freeze_GETstilesdata(sself((s5build/bdist.darwin-8.11.1-i386/egg/TileCache/Swarm.pys freeze_PUTJscCs)tid|iii|i|iŒSdS(Ns !31pHLLLL(sstructspacksselfstileslayersnameslevelsbox(sself((s5build/bdist.darwin-8.11.1-i386/egg/TileCache/Swarm.pys freeze_DELETEMs (s__name__s __module__stypessheadersstructscalcsizes header_lenstilespecs tilespec_lensNones__init__s_thaws classmethodsthaws thaw_PINGs thaw_PONGsthaw_GETsthaw_PUTs thaw_DELETEsfreezes freeze_PINGs freeze_PONGs freeze_GETs freeze_PUTs freeze_DELETE(((s5build/bdist.darwin-8.11.1-i386/egg/TileCache/Swarm.pysMessage s&            sPeercBs tZdZeedd„ZRS(Nif10.0cCs:||_||_t|ƒ|_d|_|i|_dS(Nl(saddresssselfskeysfloatsweightsseq_ids min_timeoutstimeout(sselfskeysaddresssweight((s5build/bdist.darwin-8.11.1-i386/egg/TileCache/Swarm.pys__init__Ss    (s__name__s __module__s min_timeoutsNones__init__(((s5build/bdist.darwin-8.11.1-i386/egg/TileCache/Swarm.pysPeerQssClientcBsøtZdZdZed„Zd„Zed„Zd„Zd„Z d„Z d „Z d „Z d „Z d „Zd „Zd„Zd„Zed„Zed„Zd„Zd„Zd„Zd„Zd„Zd„Zd„Zd„Zd„ZRS(Ni@icKsVti||ttiƒƒ|_g|_h|_h|_ ||_ t |_ dS(N(sPeers__init__sselfskwargsslongstimesseq_idsringspeerssrequestssservicesconfigsNonesserver(sselfsserviceskwargs((s5build/bdist.darwin-8.11.1-i386/egg/TileCache/Swarm.pys__init__^s    cCs<|itid|i|i|iƒ}t|ƒi ƒSdS(NsxHLL( stileslayersstructspackszsxsysidsshasdigest(sselfstilesid((s5build/bdist.darwin-8.11.1-i386/egg/TileCache/Swarm.pystile_keygs(cCs,|id7_t||i|i|ƒSdS(Ni(sselfsseq_idsMessagestypeskeystile(sselfstypestile((s5build/bdist.darwin-8.11.1-i386/egg/TileCache/Swarm.pysmessagekscCs!|io|id8_ndS(Ni(speerstimeout(sselfspeer((s5build/bdist.darwin-8.11.1-i386/egg/TileCache/Swarm.pys drop_timeoutos cCs|id|i|ƒdS(Nf1.0(sselfsschedules drop_timeoutspeer(sselfspeer((s5build/bdist.darwin-8.11.1-i386/egg/TileCache/Swarm.pysschedule_timeoutrscCsH|i|ƒ}||ijog|i|–s(sdictsmapspeerss new_peersskeyspeersselfsrebalance_peers(sselfspeerss new_peersskeyspeer((s5build/bdist.darwin-8.11.1-i386/egg/TileCache/Swarm.pys set_peers•s   c Csóg}|iiƒ}tgi}|D]}||iƒq&~ƒd}x|D]ˆ}|i||i }|ii|i |fƒxRtdt|ƒƒD];}t|i t|ƒƒiƒ} |ii| |fƒq™WqPW|iƒ||_dS(Nf1.0i(sringsselfspeerssvaluesssumsappends_[1]spsweights total_weightspeersmax_ring_insertss normal_weightskeysrangesintsisshaschrsdigestssubkeyssort( sselfs normal_weightspeerssis_[1]sps total_weightspeersringssubkey((s5build/bdist.darwin-8.11.1-i386/egg/TileCache/Swarm.pysrebalance_peers¤s4 cCsåt|ƒtjo|i|ƒ}nt|i|fƒ}|}g}x“t |ƒ|jo|i|d}|i o|i|ijo|i|ƒn|t |iƒjo d}n |d7}||joPqJqJW|SdS(Nii(stypeskeysTilesselfstile_keys bisect_leftsringsstartscursorsselectedslenscountspeerstimeoutsappend(sselfskeyscountsselectedspeerscursorsstart((s5build/bdist.darwin-8.11.1-i386/egg/TileCache/Swarm.pys select_peers±s    cCsnt|ƒo|i||ƒnxF|i|ƒD]5}|id|ƒ}|i ||ƒ|i |ƒq1WdS(NsGET( scallablescallbacksselfsset_put_callbackstiles select_peersstargetsmessagesmsgssendsschedule_timeout(sselfstilescallbackstargetsmsg((s5build/bdist.darwin-8.11.1-i386/egg/TileCache/Swarm.pyssend_GETÂs cCs@x9|i|ƒD](}|id|ƒ}|i||ƒqWdS(NsPUT(sselfs select_peersstilestargetsmessagesmsgssend(sselfstilesmsgstarget((s5build/bdist.darwin-8.11.1-i386/egg/TileCache/Swarm.pyssend_PUTÊscCs*|i||idƒƒ|i|ƒdS(NsPING(sselfssendspeersmessagesschedule_timeout(sselfspeer((s5build/bdist.darwin-8.11.1-i386/egg/TileCache/Swarm.pys send_PINGÏscCs?|idƒ}|i|_|i|i}|i ||ƒdS(NsPONG( sselfsmessagesmsgspingsseq_idsping_idspeersskeyspeerssend(sselfspingsmsgspeer((s5build/bdist.darwin-8.11.1-i386/egg/TileCache/Swarm.pys send_PONGÓs cCsg|\}}ti||iiƒ}|i |i }|i |_ t|d|iƒ}|||ƒdS(Nshandle_(shostsportsMessagesthawsthunksselfsconfigslayerssmsgspeersskeyspeers max_timeoutstimeoutsgetattrstypesdispatch(sselfsthunks.4shostsportspeersdispatchsmsg((s5build/bdist.darwin-8.11.1-i386/egg/TileCache/Swarm.pyshandleÙs  cCse|iii|iƒ}|o5||i_|id|iƒ}|i ||ƒn|i |ƒdS(NsPUT( sselfsconfigscachesgetsmsgstilesdatasmessagesreplyssendspeers send_PONG(sselfspeersmsgsdatasreply((s5build/bdist.darwin-8.11.1-i386/egg/TileCache/Swarm.pys handle_GETás  cCs3|iii|i|iiƒ|i|iƒdS(N(sselfsconfigscachessetsmsgstilesdatashandle_put_callbacks(sselfspeersmsg((s5build/bdist.darwin-8.11.1-i386/egg/TileCache/Swarm.pys handle_PUTêscCs|i|ƒdS(N(sselfs send_PONGsmsg(sselfspeersmsg((s5build/bdist.darwin-8.11.1-i386/egg/TileCache/Swarm.pys handle_PINGîscCsdS(N((sselfspeersmsg((s5build/bdist.darwin-8.11.1-i386/egg/TileCache/Swarm.pys handle_PONGñscCsdS(N((sselfspeersmsg((s5build/bdist.darwin-8.11.1-i386/egg/TileCache/Swarm.pys handle_DELETEõs(s__name__s __module__smax_ring_insertss replicationsNones__init__stile_keysmessages drop_timeoutsschedule_timeoutsset_put_callbackstrigger_put_callbacksssendsschedules load_peerssload_peers_from_strings set_peerssrebalance_peerss select_peersssend_GETssend_PUTs send_PINGs send_PONGshandles handle_GETs handle_PUTs handle_PINGs handle_PONGs handle_DELETE(((s5build/bdist.darwin-8.11.1-i386/egg/TileCache/Swarm.pysClientZs4                    ( sstructstimesshasbisects bisect_leftsLayersTilesClientsWMSsServicesobjectsMessagesPeer( sLayersstructsServicesWMSs bisect_leftsshasClientsPeerstimesTilesMessage((s5build/bdist.darwin-8.11.1-i386/egg/TileCache/Swarm.pys?s    G PKê’7eq±íu u TileCache/tilecache.cfg# Configuration for MC TileCache # TileCache can load Layers or Caches from anywhere in sys.path. If you # prefer to load from somewhere which is *not* on sys.path, you can use # the path configuration paramter to set a comma-seperated list of # filesystem paths which you want prepended to sys.path. #[tilecache_options] #path=/home/you # [cache] section (mandatory!) # type=DiskCache (works out of the box) # base= # *or* # type=Memcached (you'll need memcache.py and memcached running!) # servers=192.168.1.1:11211 [cache] type=Disk base=/tmp/tilecache # [layername] -- all other sections are named layers # # type={MapServerLayer,WMSLayer} # *** if you want to use MapServerLayer, you *must* have Python mapscript # installed and available *** # # mapfile= # url= # layers=[,,,...] # *** optional iff layername if what # your data source calls the layer ** # extension={png,jpeg,gif} *** defaults to "png" *** # size=256,256 *** defaults to 256x256 *** # bbox=-180.0,-90.0,180.0,90.0 *** defaults to world in lon/lat *** # srs=EPSG:4326 *** defaults to EPSG:4326 *** # levels=20 *** defaults to 20 zoom levels *** # resolutions=0.1,0.05,0.025,... *** defaults to global profile *** # metaTile=true *** metatiling off by default # requires python-imaging *** # metaSize=5,5 *** size of metatile in tiles # defaults to 5 x 5 *** # metaBuffer=10 *** size of metatile buffer in px *** # mime_type=image/png *** by default, the mime type is image/extension *** # *** but you may want to set extension=png8 for *** # *** GeoServer WMS, and this lets you set the *** # *** mime_type seperately. *** # The following is a demonstration of a layer which would be generated # according to the 'Google projection'. Note that EPSG:900913 is a play # on a lowercase 'google' in "leet-speak" -- it is not an official EPSG # code. More information on the projection available at: # http://spatialreference.org/ref/user/google-projection/ # [google-tiles] # type=WMS # url=http://localhost/cgi-bin/mapserv?map=/mapdata/world.map # layers=world # bbox=-20037508.3427892,-20037508.3427892,20037508.3427892,20037508.3427892 # maxResolution=156543.0339 # srs=EPSG:900913 # Standard MapServer layer configuration. # [vmap0] # type=MapServer # layers=vmap0 # mapfile=/var/www/vmap0.map [basic] type=WMS url=http://labs.metacarta.com/wms/vmap0 extension=png PK9…7TileCache/Caches/__init__.pyPK˜X–7|K{{TileCache/Caches/__init__.pyc;ò ßLVGc@sdS(N((((s?build/bdist.darwin-8.11.1-i386/egg/TileCache/Caches/__init__.pys?sPK¬=‡7€‹6 „ „ TileCache/Caches/Disk.pyfrom TileCache.Cache import Cache import sys, os, time class Disk (Cache): def __init__ (self, base = None, umask = '002', **kwargs): Cache.__init__(self, **kwargs) self.basedir = base self.umask = int(umask, 0) if sys.platform.startswith("java"): from java.io import File self.file_module = File self.platform = "jython" else: self.platform = "cpython" if not self.access(base, 'read'): self.makedirs(base) def makedirs(self, path): old_umask = os.umask(self.umask) os.makedirs(path) os.umask(old_umask) def access(self, path, type='read'): if self.platform == "jython": if type == "read": return self.file_module(path).canRead() else: return self.file_module(path).canWrite() else: if type =="read": return os.access(path, os.R_OK) else: return os.access(path, os.W_OK) def getKey (self, tile): components = ( self.basedir, tile.layer.name, "%02d" % tile.z, "%03d" % int(tile.x / 1000000), "%03d" % (int(tile.x / 1000) % 1000), "%03d" % (int(tile.x) % 1000), "%03d" % int(tile.y / 1000000), "%03d" % (int(tile.y / 1000) % 1000), "%03d.%s" % (int(tile.y) % 1000, tile.layer.extension) ) filename = os.path.join( *components ) return filename def get (self, tile): filename = self.getKey(tile) if self.access(filename, 'read'): tile.data = file(filename, "rb").read() return tile.data else: return None def set (self, tile, data): if self.readonly: return data filename = self.getKey(tile) dirname = os.path.dirname(filename) if not self.access(dirname, 'write'): self.makedirs(dirname) tmpfile = filename + ".%d.tmp" % os.getpid() old_umask = os.umask(self.umask) output = file(tmpfile, "wb") output.write(data) output.close() os.umask( old_umask ); try: os.rename(tmpfile, filename) except OSError: os.unlink(filename) os.rename(tmpfile, filename) tile.data = data return data def delete (self, tile): filename = self.getKey(tile) if self.access(filename, 'read'): os.unlink(filename) def attemptLock (self, tile): name = self.getLockName(tile) try: self.makedirs(name) return True except OSError: pass try: st = os.stat(name) if st.st_ctime + self.stale < time.time(): warnings.warn("removing stale lock %s" % name) # remove stale lock self.unlock() self.makedirs(name) return True except OSError: pass return False def unlock (self, tile): name = self.getLockName(tile) try: os.rmdir(name) except OSError, E: print >>sys.stderr, "unlock %s failed: %s" % (name, str(E)) PK˜X–7CR¹°°TileCache/Caches/Disk.pyc;ò e@YGc@sBdklZdkZdkZdkZdefd„ƒYZdS((sCacheNsDiskcBsbtZedd„Zd„Zdd„Zd„Zd„Zd„Zd „Z d „Z d „Z RS( Ns002cKs“ti||||_t|dƒ|_ti i dƒo#dk l }||_ d|_ n d|_ |i|dƒ o|i|ƒndS(Nisjava(sFilesjythonscpythonsread(sCaches__init__sselfskwargssbasesbasedirsintsumaskssyssplatforms startswithsjava.iosFiles file_modulesaccesssmakedirs(sselfsbasesumaskskwargssFile((s;build/bdist.darwin-8.11.1-i386/egg/TileCache/Caches/Disk.pys__init__s     cCs0ti|iƒ}ti|ƒti|ƒdS(N(sossumasksselfs old_umasksmakedirsspath(sselfspaths old_umask((s;build/bdist.darwin-8.11.1-i386/egg/TileCache/Caches/Disk.pysmakedirss sreadcCs†|idjo;|djo|i|ƒiƒSq‚|i|ƒiƒSn8|djoti|ti ƒSnti|ti ƒSdS(Nsjythonsread( sselfsplatformstypes file_modulespathscanReadscanWritesossaccesssR_OKsW_OK(sselfspathstype((s;build/bdist.darwin-8.11.1-i386/egg/TileCache/Caches/Disk.pysaccesss  c CsÅ|i|iid|idt|idƒdt|idƒddt|iƒddt|idƒdt|idƒddt|iƒd|ii ff }t i i |Œ}|SdS(Ns%02ds%03di@Biès%03d.%s(sselfsbasedirstileslayersnameszsintsxsys extensions componentssosspathsjoinsfilename(sselfstilesfilenames components((s;build/bdist.darwin-8.11.1-i386/egg/TileCache/Caches/Disk.pysgetKey%s« cCsM|i|ƒ}|i|dƒo#t|dƒiƒ|_|iSntSdS(Nsreadsrb( sselfsgetKeystilesfilenamesaccesssfilesreadsdatasNone(sselfstilesfilename((s;build/bdist.darwin-8.11.1-i386/egg/TileCache/Caches/Disk.pysget3s  cCs |io|Sn|i|ƒ}tii|ƒ}|i |dƒ o|i |ƒn|dti ƒ}ti |i ƒ}t|dƒ}|i|ƒ|iƒti |ƒyti||ƒWn0tj o$ti|ƒti||ƒnX||_|SdS(Nswrites.%d.tmpswb(sselfsreadonlysdatasgetKeystilesfilenamesosspathsdirnamesaccesssmakedirssgetpidstmpfilesumasks old_umasksfilesoutputswritesclosesrenamesOSErrorsunlink(sselfstilesdatastmpfilesfilenames old_umasksoutputsdirname((s;build/bdist.darwin-8.11.1-i386/egg/TileCache/Caches/Disk.pysset;s&      cCs7|i|ƒ}|i|dƒoti|ƒndS(Nsread(sselfsgetKeystilesfilenamesaccesssossunlink(sselfstilesfilename((s;build/bdist.darwin-8.11.1-i386/egg/TileCache/Caches/Disk.pysdeleteOscCs¸|i|ƒ}y|i|ƒtSWntj onXy`ti|ƒ}|i |i t i ƒjo0t id|ƒ|iƒ|i|ƒtSnWntj onXtSdS(Nsremoving stale lock %s(sselfs getLockNamestilesnamesmakedirssTruesOSErrorsossstatsstsst_ctimesstalestimeswarningsswarnsunlocksFalse(sselfstilesnamesst((s;build/bdist.darwin-8.11.1-i386/egg/TileCache/Caches/Disk.pys attemptLockTs     cCsY|i|ƒ}yti|ƒWn2tj o&}ti d|t |ƒfIJnXdS(Nsunlock %s failed: %s( sselfs getLockNamestilesnamesossrmdirsOSErrorsEssyssstderrsstr(sselfstilesEsname((s;build/bdist.darwin-8.11.1-i386/egg/TileCache/Caches/Disk.pysunlockgs ( s__name__s __module__sNones__init__smakedirssaccesssgetKeysgetssetsdeletes attemptLocksunlock(((s;build/bdist.darwin-8.11.1-i386/egg/TileCache/Caches/Disk.pysDisks      (sTileCache.CachesCachessyssosstimesDisk(ssyssCachesossDiskstime((s;build/bdist.darwin-8.11.1-i386/egg/TileCache/Caches/Disk.pys?s PK¬=‡7µ¦»--TileCache/Caches/Memcached.pyfrom TileCache.Cache import Cache import time class Memcached(Cache): def __init__ (self, servers = ['127.0.0.1:11211'], **kwargs): Cache.__init__(self, **kwargs) import memcache if type(servers) is str: servers = map(str.strip, servers.split(",")) self.cache = memcache.Client(servers, debug=0) def getKey(self, tile): return "/".join(map(str, [tile.layer.name, tile.x, tile.y, tile.z])) def get(self, tile): key = self.getKey(tile) tile.data = self.cache.get(key) return tile.data def set(self, tile, data): if self.readonly: return data key = self.getKey(tile) self.cache.set(key, data) return data def delete(self, tile): key = self.getKey(tile) self.cache.delete(key) def attemptLock (self, tile): return self.cache.add( self.getLockName(tile), "0", time.time() + self.timeout) def unlock (self, tile): self.cache.delete( self.getLockName() ) PK˜X–72ÐÝØ Ø TileCache/Caches/Memcached.pyc;ò e@YGc@s0dklZdkZdefd„ƒYZdS((sCacheNs MemcachedcBsMtZdgd„Zd„Zd„Zd„Zd„Zd„Zd„ZRS( Ns127.0.0.1:11211cKsgti||dk}t|ƒtjotti |i dƒƒ}n|i |ddƒ|_ dS(Ns,sdebugi( sCaches__init__sselfskwargssmemcachestypesserverssstrsmapsstripssplitsClientscache(sselfsserversskwargssmemcache((s@build/bdist.darwin-8.11.1-i386/egg/TileCache/Caches/Memcached.pys__init__s  cCs5ditt|ii|i|i|igƒƒSdS(Ns/( sjoinsmapsstrstileslayersnamesxsysz(sselfstile((s@build/bdist.darwin-8.11.1-i386/egg/TileCache/Caches/Memcached.pysgetKey scCs/|i|ƒ}|ii|ƒ|_|iSdS(N(sselfsgetKeystileskeyscachesgetsdata(sselfstileskey((s@build/bdist.darwin-8.11.1-i386/egg/TileCache/Caches/Memcached.pysgetscCs<|io|Sn|i|ƒ}|ii||ƒ|SdS(N(sselfsreadonlysdatasgetKeystileskeyscachesset(sselfstilesdataskey((s@build/bdist.darwin-8.11.1-i386/egg/TileCache/Caches/Memcached.pyssets  cCs#|i|ƒ}|ii|ƒdS(N(sselfsgetKeystileskeyscachesdelete(sselfstileskey((s@build/bdist.darwin-8.11.1-i386/egg/TileCache/Caches/Memcached.pysdeletescCs0|ii|i|ƒdtiƒ|iƒSdS(Ns0(sselfscachesadds getLockNamestilestimestimeout(sselfstile((s@build/bdist.darwin-8.11.1-i386/egg/TileCache/Caches/Memcached.pys attemptLockscCs|ii|iƒƒdS(N(sselfscachesdeletes getLockName(sselfstile((s@build/bdist.darwin-8.11.1-i386/egg/TileCache/Caches/Memcached.pysunlock!s( s__name__s __module__s__init__sgetKeysgetssetsdeletes attemptLocksunlock(((s@build/bdist.darwin-8.11.1-i386/egg/TileCache/Caches/Memcached.pys Memcacheds     (sTileCache.CachesCachestimes Memcached(sCaches Memcachedstime((s@build/bdist.darwin-8.11.1-i386/egg/TileCache/Caches/Memcached.pys?s  PK…7TileCache/Layers/__init__.pyPK˜X–7uo¡TileCache/Layers/__init__.pyc;ò zLVGc@sdS(N((((s?build/bdist.darwin-8.11.1-i386/egg/TileCache/Layers/__init__.pys?sPK…7ö\¦6ËËTileCache/Layers/ArcXML.pyfrom TileCache.Layer import MetaLayer from TileCache.Service import TileCacheException import urllib import xml.dom.minidom as m class ArcXML(MetaLayer): def __init__ (self, name, url = None, off_layers = "", **kwargs): MetaLayer.__init__(self, name, **kwargs) self.url = url self.off_layers = off_layers def renderTile(self, tile): layers = [] off_layers = [] for id in self.layers.split(","): if id.strip(): layers.append('' % id) for id in self.off_layers.split(","): if id.strip(): off_layers.append('' % id) bbox = tile.bounds() xml = """ %s %s """ % (bbox[0], bbox[1], bbox[2], bbox[3], tile.size()[0], tile.size()[1], "\n".join(layers), "\n".join(off_layers)) try: xmldata = urllib.urlopen(self.url, xml).read() except Exception, E: raise TileCacheException("Error fetching URL. Exception was: %s\n Input XML:\n %s " % (E, xml)) try: doc = m.parseString(xmldata) imgURL = doc.getElementsByTagName("OUTPUT")[0].attributes['url'].value except Exception, E: raise TileCacheException("Error fetching URL. Exception was: %s\n Output XML: \n%s\n\nInput XML:\n %s " % (E, xmldata, xml)) tile.data = urllib.urlopen(imgURL).read() return tile.data PK˜X–7ªV¸ŸS S TileCache/Layers/ArcXML.pyc;ò s=VGc@sLdklZdklZdkZdkiiZdefd„ƒYZ dS((s MetaLayer(sTileCacheExceptionNsArcXMLcBs tZedd„Zd„ZRS(NscKs)ti|||||_||_dS(N(s MetaLayers__init__sselfsnameskwargssurls off_layers(sselfsnamesurls off_layersskwargs((s=build/bdist.darwin-8.11.1-i386/egg/TileCache/Layers/ArcXML.pys__init__s c Cs¿g}g}x<|iidƒD](} | iƒo|id| ƒqqWx<|iidƒD](} | iƒo|id| ƒq^q^W|iƒ}d|d|d|d|d|i ƒd|i ƒdd i |ƒd i |ƒf}yt i|i|ƒiƒ}Wn+tj o}td ||fƒ‚nXy0ti|ƒ}|id ƒdid i} Wn.tj o"}td |||fƒ‚nXt i| ƒiƒ|_|iSdS(Ns,s#s$s  %s %s iiiis s6Error fetching URL. Exception was: %s Input XML: %s sOUTPUTsurlsGError fetching URL. Exception was: %s Output XML: %s Input XML: %s (slayerss off_layerssselfssplitsidsstripsappendstilesboundssbboxssizesjoinsxmlsurllibsurlopensurlsreadsxmldatas ExceptionsEsTileCacheExceptionsms parseStringsdocsgetElementsByTagNames attributessvaluesimgURLsdata( sselfstileslayerssxmlsEsdocsxmldatasbboxs off_layerssidsimgURL((s=build/bdist.darwin-8.11.1-i386/egg/TileCache/Layers/ArcXML.pys renderTile s.   X!(s__name__s __module__sNones__init__s renderTile(((s=build/bdist.darwin-8.11.1-i386/egg/TileCache/Layers/ArcXML.pysArcXMLs( sTileCache.Layers MetaLayersTileCache.ServicesTileCacheExceptionsurllibsxml.dom.minidomsdomsminidomsmsArcXML(s MetaLayersmsArcXMLsurllibsTileCacheException((s=build/bdist.darwin-8.11.1-i386/egg/TileCache/Layers/ArcXML.pys?s   PK…7CüÜž ž TileCache/Layers/Image.pyfrom TileCache.Layer import MetaLayer class Image(MetaLayer): """The ImageLayer allows you to set up any image file in TileCache. All you need is an image, and a geographic bounds (filebounds), Which is passed in as a single, comma seperated string in the form minx,miny,maxx,maxy.""" def __init__ (self, name, file = None, filebounds = "-180,-90,180,90", transparency = False, scaling = "nearest", **kwargs): import Image MetaLayer.__init__(self, name, **kwargs) self.file = file self.filebounds = map(float,filebounds.split(",")) self.image = Image.open(self.file) self.image_size = self.image.size self.image_res = [(self.filebounds[2] - self.filebounds[0]) / self.image_size[0], (self.filebounds[3] - self.filebounds[1]) / self.image_size[1] ] self.scaling = scaling.lower() if isinstance(transparency, str): transparency = transparency.lower() in ("true", "yes", "1") self.transparency = transparency def renderTile(self, tile): import Image, StringIO bounds = tile.bounds() size = tile.size() min_x = (bounds[0] - self.filebounds[0]) / self.image_res[0] min_y = (self.filebounds[3] - bounds[3]) / self.image_res[1] max_x = (bounds[2] - self.filebounds[0]) / self.image_res[0] max_y = (self.filebounds[3] - bounds[1]) / self.image_res[1] if self.scaling == "bilinear": scaling = Image.BILINEAR elif self.scaling == "bicubic": scaling = Image.BICUBIC elif self.scaling == "antialias": scaling = Image.ANTIALIAS else: scaling = Image.NEAREST crop_size = (max_x-min_x, max_y-min_y) if min(min_x, min_y, max_x, max_y) < 0: if self.transparency and self.image.mode in ("L", "RGB"): self.image.putalpha(Image.new("L", self.image_size, 255)); sub = self.image.transform(crop_size, Image.EXTENT, (min_x, min_y, max_x, max_y)) else: sub = self.image.crop((min_x, min_y, max_x, max_y)); if crop_size[0] < size[0] and crop_size[1] < size[1] and self.scaling == "antialias": scaling = Image.BICUBIC sub = sub.resize(size, scaling) buffer = StringIO.StringIO() if self.image.info.has_key('transparency'): sub.save(buffer, self.extension, transparency=self.image.info['transparency']) else: sub.save(buffer, self.extension) buffer.seek(0) tile.data = buffer.read() return tile.data PK˜X–7°Y`D D TileCache/Layers/Image.pyc;ò s=VGc@s'dklZdefd„ƒYZdS((s MetaLayersImagecBs,tZdZededd„Zd„ZRS(sîThe ImageLayer allows you to set up any image file in TileCache. All you need is an image, and a geographic bounds (filebounds), Which is passed in as a single, comma seperated string in the form minx,miny,maxx,maxy.s-180,-90,180,90snearestcKsødk}ti|||||_tt|i dƒƒ|_ |i |iƒ|_ |i i |_|i d|i d|id|i d|i d|idg|_|iƒ|_t|tƒo|iƒdddfj}n||_dS( Ns,iiiistruesyess1(sImages MetaLayers__init__sselfsnameskwargssfilesmapsfloats fileboundsssplitsopensimagessizes image_sizes image_ressscalingslowers isinstances transparencysstr(sselfsnamesfiles fileboundss transparencysscalingskwargssImage((s<build/bdist.darwin-8.11.1-i386/egg/TileCache/Layers/Image.pys__init__ s  IcCs¨dk} dk}|iƒ}|iƒ} |d|id|id}|id|d|id}|d|id|id} |id|d|id} |i djo | i }nD|i djo | i}n'|i djo | i}n | i}| || |f} t||| | ƒdjot|io|iidd fjo&|ii| id|id ƒƒn|ii| | i||| | fƒ}n|ii||| | fƒ}| d| djo"| d| djo |i djo | i}n|i| |ƒ}|iƒ}|iii d ƒo'|i!||i"d |iid ƒn|i!||i"ƒ|i#dƒ|i$ƒ|_%|i%SdS( Niiiisbilinearsbicubics antialiassLsRGBiÿs transparency(&sImagesStringIOstilesboundsssizesselfs fileboundss image_ressmin_xsmin_ysmax_xsmax_ysscalingsBILINEARsBICUBICs ANTIALIASsNEARESTs crop_sizesmins transparencysimagesmodesputalphasnews image_sizes transformsEXTENTssubscropsresizesbuffersinfoshas_keyssaves extensionsseeksreadsdata(sselfstilessubsmin_xsmin_ysStringIOsbuffersboundssscalings crop_sizesmax_ysImagesmax_xssize((s<build/bdist.darwin-8.11.1-i386/egg/TileCache/Layers/Image.pys renderTiles<          #&+:  ' (s__name__s __module__s__doc__sNonesFalses__init__s renderTile(((s<build/bdist.darwin-8.11.1-i386/egg/TileCache/Layers/Image.pysImages N(sTileCache.Layers MetaLayersImage(sImages MetaLayer((s<build/bdist.darwin-8.11.1-i386/egg/TileCache/Layers/Image.pys?s PK¬=‡7Åà˪ªTileCache/Layers/Mapnik.pyfrom TileCache.Layer import MetaLayer class Mapnik(MetaLayer): def __init__ (self, name, mapfile = None, projection = None, fonts = None, **kwargs): MetaLayer.__init__(self, name, **kwargs) self.mapfile = mapfile self.mapnik = None self.projection = projection if fonts: self.fonts = fonts.split(",") else: self.fonts = [] def renderTile(self, tile): import mapnik, StringIO import PIL.Image if self.mapnik: m = self.mapnik else: if self.fonts: engine = mapnik.FontEngine.instance() for font in self.fonts: engine.register_font(font) # Init it as 0,0 m = mapnik.Map( 0, 0 ) mapnik.load_map(m,self.mapfile) if self.projection: m.srs = self.projection # Restrict layer list, if requested if self.layers and self.layers != self.name: layers = self.layers.split(",") for layer_num in range(len(m.layers)-1, -1, -1): l = m.layers[layer_num] if l.name not in layers: del m.layers[layer_num] if self.debug: print >>sys.stderr, "Removed layer %s loaded from %s, not in list: %s" % (l.name, self.mapfile, layers) # this will insure that it gets cached in mod_python self.mapnik = m # Set the mapnik size to match the size of the current tile m.width = tile.size()[0] m.height = tile.size()[1] bbox = tile.bounds() bbox = mapnik.Envelope(bbox[0], bbox[1], bbox[2], bbox[3]) m.zoom_to_box(bbox) im = mapnik.Image( *tile.size() ) mapnik.render(m, im) im = PIL.Image.fromstring('RGBA', tile.size(), mapnik.rawdata(im)) buffer = StringIO.StringIO() im.save(buffer, self.extension) buffer.seek(0) tile.data = buffer.read() return tile.data PK˜X–70‚ ˆ¿ ¿ TileCache/Layers/Mapnik.pyc;ò e@YGc@s'dklZdefd„ƒYZdS((s MetaLayersMapnikcBs#tZeeed„Zd„ZRS(NcKsXti|||||_t|_||_|o|i dƒ|_ n g|_ dS(Ns,( s MetaLayers__init__sselfsnameskwargssmapfilesNonesmapniks projectionsfontsssplit(sselfsnamesmapfiles projectionsfontsskwargs((s=build/bdist.darwin-8.11.1-i386/egg/TileCache/Layers/Mapnik.pys__init__s   cCsgdk} dk}dk}|io |i}n=|io4| iiƒ}x"|iD]} |i | ƒqUWn| i ddƒ}| i ||iƒ|io|i|_n|io|i|ijo™|iidƒ}x„tt|iƒdddƒD]_}|i|} | i|jo|i|=n|io$tid| i|i|fIJqþqþWn||_|iƒd|_|iƒd|_|iƒ} | i!| d| d| d| dƒ} |i"| ƒ| i#|iƒŒ} | i%|| ƒ|i#i&d|iƒ| i'| ƒƒ} |iƒ}| i)||i*ƒ|i+dƒ|i,ƒ|_-|i-SdS( Nis,iiÿÿÿÿs0Removed layer %s loaded from %s, not in list: %siisRGBA(.smapniksStringIOs PIL.ImagesPILsselfsmsfontss FontEnginesinstancesenginesfonts register_fontsMapsload_mapsmapfiles projectionssrsslayerssnamessplitsrangeslens layer_numslsdebugssyssstderrstilessizeswidthsheightsboundssbboxsEnvelopes zoom_to_boxsImagesimsrenders fromstringsrawdatasbufferssaves extensionsseeksreadsdata(sselfstilesengineslayerssPILsStringIOsbuffers layer_numsmslsimsbboxsfontsmapnik((s=build/bdist.darwin-8.11.1-i386/egg/TileCache/Layers/Mapnik.pys renderTilesH         ,  ( '  (s__name__s __module__sNones__init__s renderTile(((s=build/bdist.darwin-8.11.1-i386/egg/TileCache/Layers/Mapnik.pysMapniks N(sTileCache.Layers MetaLayersMapnik(s MetaLayersMapnik((s=build/bdist.darwin-8.11.1-i386/egg/TileCache/Layers/Mapnik.pys?s PKT¸‰7+”É>;;TileCache/Layers/MapServer.pyfrom TileCache.Layer import MetaLayer class MapServer(MetaLayer): def __init__ (self, name, mapfile = None, styles = "", **kwargs): MetaLayer.__init__(self, name, **kwargs) self.mapfile = mapfile self.styles = styles def get_map(self, tile): # tile is unused here but might be used in a subclass # where the mapfile config depends on the tile extents or layer import mapscript wms = mapscript.mapObj(self.mapfile) if self.metaBuffer: try: # if the metadata is already set, don't override. wms.getMetaData("labelcache_map_edge_buffer") except mapscript._mapscript.MapServerError: # We stick an extra buffer of 5px in there because in the case # of shields, we want to account for when the shield could get # cut even though the label that the shield is on isn't. buffer = -max(self.metaBuffer[0], self.metaBuffer[1]) - 5 wms.setMetaData("labelcache_map_edge_buffer", str(buffer)) return wms def get_request(self, tile): import mapscript req = mapscript.OWSRequest() req.setParameter("bbox", tile.bbox()) req.setParameter("width", str(tile.size()[0])) req.setParameter("height", str(tile.size()[1])) req.setParameter("srs", self.srs) req.setParameter("format", self.format()) req.setParameter("layers", self.layers) req.setParameter("styles", self.styles) req.setParameter("request", "GetMap") return req def renderTile(self, tile): wms = self.get_map(tile) req = self.get_request(tile) wms.loadOWSParameters(req) mapImage = wms.draw() tile.data = mapImage.getBytes() return tile.data PK˜X–7Ë&ôeæ æ TileCache/Layers/MapServer.pyc;ò `º\Gc@s'dklZdefd„ƒYZdS((s MetaLayers MapServercBs2tZedd„Zd„Zd„Zd„ZRS(NscKs)ti|||||_||_dS(N(s MetaLayers__init__sselfsnameskwargssmapfilesstyles(sselfsnamesmapfilesstylesskwargs((s@build/bdist.darwin-8.11.1-i386/egg/TileCache/Layers/MapServer.pys__init__s cCs–dk}|i|iƒ}|ioiy|idƒWqŽ|iij o?t |id|idƒ d}|i dt |ƒƒqŽXn|SdS(Nslabelcache_map_edge_bufferiii( s mapscriptsmapObjsselfsmapfileswmss metaBuffers getMetaDatas _mapscriptsMapServerErrorsmaxsbuffers setMetaDatasstr(sselfstileswmssbuffers mapscript((s@build/bdist.darwin-8.11.1-i386/egg/TileCache/Layers/MapServer.pysget_map s  "cCsÒdk}|iƒ}|id|iƒƒ|idt|iƒdƒƒ|idt|iƒdƒƒ|id|i ƒ|id|i ƒƒ|id|i ƒ|id |i ƒ|id d ƒ|SdS( NsbboxswidthisheightissrssformatslayerssstylessrequestsGetMap( s mapscripts OWSRequestsreqs setParameterstilesbboxsstrssizesselfssrssformatslayerssstyles(sselfstilesreqs mapscript((s@build/bdist.darwin-8.11.1-i386/egg/TileCache/Layers/MapServer.pys get_requests    cCsQ|i|ƒ}|i|ƒ}|i|ƒ|iƒ}|i ƒ|_ |i SdS(N( sselfsget_mapstileswmss get_requestsreqsloadOWSParameterssdrawsmapImagesgetBytessdata(sselfstileswmssreqsmapImage((s@build/bdist.darwin-8.11.1-i386/egg/TileCache/Layers/MapServer.pys renderTile's   (s__name__s __module__sNones__init__sget_maps get_requests renderTile(((s@build/bdist.darwin-8.11.1-i386/egg/TileCache/Layers/MapServer.pys MapServers  N(sTileCache.Layers MetaLayers MapServer(s MapServers MetaLayer((s@build/bdist.darwin-8.11.1-i386/egg/TileCache/Layers/MapServer.pys?s PK…7³9^³??TileCache/Layers/WMS.pyfrom TileCache.Layer import MetaLayer import TileCache.Client as WMSClient class WMS(MetaLayer): def __init__ (self, name, url = None, **kwargs): MetaLayer.__init__(self, name, **kwargs) self.url = url def renderTile(self, tile): wms = WMSClient.WMS( self.url, { "bbox": tile.bbox(), "width": tile.size()[0], "height": tile.size()[1], "srs": self.srs, "format": self.format(), "layers": self.layers, } ) tile.data, response = wms.fetch() return tile.data PK˜X–7xbFFWWTileCache/Layers/WMS.pyc;ò s=VGc@s3dklZdkiZdefd„ƒYZdS((s MetaLayerNsWMScBstZed„Zd„ZRS(NcKs ti|||||_dS(N(s MetaLayers__init__sselfsnameskwargssurl(sselfsnamesurlskwargs((s:build/bdist.darwin-8.11.1-i386/egg/TileCache/Layers/WMS.pys__init__scCs‘ti|ihd|iƒ<d|iƒd<d|iƒd<d|i<d|iƒ<d|i <ƒ}|i ƒ\|_ }|i SdS( Nsbboxswidthisheightissrssformatslayers(s WMSClientsWMSsselfsurlstilesbboxssizessrssformatslayersswmssfetchsdatasresponse(sselfstileswmssresponse((s:build/bdist.darwin-8.11.1-i386/egg/TileCache/Layers/WMS.pys renderTile sq(s__name__s __module__sNones__init__s renderTile(((s:build/bdist.darwin-8.11.1-i386/egg/TileCache/Layers/WMS.pysWMSs (sTileCache.Layers MetaLayersTileCache.ClientsClients WMSClientsWMS(sWMSs MetaLayers WMSClient((s:build/bdist.darwin-8.11.1-i386/egg/TileCache/Layers/WMS.pys?s  PK…7TileCache/Services/__init__.pyPK˜X–71é3à‘‘TileCache/Services/__init__.pyc;ò t=VGc@sdS(N((((sAbuild/bdist.darwin-8.11.1-i386/egg/TileCache/Services/__init__.pys?sPK¬=‡7î.à‚ƒƒTileCache/Services/KML.pyfrom TileCache.Service import Request, Capabilities from TileCache.Services.TMS import TMS import TileCache.Layer as Layer class KML(TMS): def parse (self, fields, path, host): tile = TMS.parse(self,fields, path, host) tiles = [ Layer.Tile(tile.layer, tile.x << 1, tile.y << 1, tile.z + 1), Layer.Tile(tile.layer, (tile.x << 1) + 1, tile.y << 1, tile.z + 1), Layer.Tile(tile.layer, (tile.x << 1) + 1, (tile.y << 1) + 1, tile.z + 1), Layer.Tile(tile.layer, tile.x << 1 , (tile.y << 1) + 1, tile.z + 1) ] network_links = [] for single_tile in tiles: b = single_tile.bounds() network_links.append(""" tile 128-1 %s%s %s%s %s/1.0.0/%s/%s/%s/%s.kml onRegion """ % (b[3], b[1], b[2], b[0], host, single_tile.layer.name, single_tile.z, single_tile.x, single_tile.y)) b = tile.bounds() kml = """ 128512 %s%s %s%s %s %s/1.0.0/%s/%s/%s/%s %s%s %s%s %s """ % (b[3], b[1], b[2], b[0], tile.z, host, tile.layer.name, tile.z, tile.x, tile.y, b[3], b[1], b[2], b[0], "\n".join(network_links)) return ("application/vnd.google-earth.kml+xml", kml) PK˜X–7Y’”± ± TileCache/Services/KML.pyc;ò e@YGc@sFdklZlZdklZdkiZdefd„ƒYZdS((sRequests Capabilities(sTMSNsKMLcBstZd„ZRS(Nc CsÜti||||ƒ} ti| i | i d>| i d>| i dƒti| i | i d>d| i d>| i dƒti| i | i d>d| i d>d| i dƒti| i | i d>| i d>d| i dƒg}g}xe|D]]}|iƒ}|id|d|d|d|d||i i|i |i |i f ƒqïW| iƒ}d|d|d|d|d| i || i i| i | i | i |d|d|d|ddi|ƒf}d|fSdS( NisÀ tile 128-1 %s%s %s%s %s/1.0.0/%s/%s/%s/%s.kml onRegion iiis| 128512 %s%s %s%s %s %s/1.0.0/%s/%s/%s/%s %s%s %s%s %s s s$application/vnd.google-earth.kml+xml(sTMSsparsesselfsfieldsspathshoststilesLayersTileslayersxsyszstiless network_linkss single_tilesboundssbsappendsnamesjoinskml( sselfsfieldsspathshoststilesskmls single_tiles network_linkssbstile((s<build/bdist.darwin-8.11.1-i386/egg/TileCache/Services/KML.pysparsesÊ O r(s__name__s __module__sparse(((s<build/bdist.darwin-8.11.1-i386/egg/TileCache/Services/KML.pysKMLs(sTileCache.ServicesRequests CapabilitiessTileCache.Services.TMSsTMSsTileCache.LayersLayersKML(sKMLsLayersTMSsRequests Capabilities((s<build/bdist.darwin-8.11.1-i386/egg/TileCache/Services/KML.pys?s  PK[Œ…7‹uY¸¹¹TileCache/Services/MGMaps.pyfrom TileCache.Service import Request, Capabilities import TileCache.Layer as Layer class MGMaps (Request): def parse (self, fields, path, host): param = {} for key in ['layer', 'zoom', 'x', 'y']: if fields.has_key(key.upper()): param[key] = fields[key.upper()] elif fields.has_key(key): param[key] = fields[key] else: param[key] = "" return self.getMap(param) def getMap (self, param): layer = self.getLayer(param["layer"]) level = int(param["zoom"]) level = 17 - level x = float(param["x"]) y = float(param["y"]) res = layer.resolutions[level] maxY = int( round( (layer.bbox[3] - layer.bbox[1]) / (res * layer.size[1]) ) ) - 1 tile = Layer.Tile(layer, x, maxY - y, level) return tile PK˜X–7ªÈsÖ™™TileCache/Services/MGMaps.pyc;ò 'WGc@s9dklZlZdkiZdefd„ƒYZdS((sRequests CapabilitiesNsMGMapscBstZd„Zd„ZRS(NcCsŽh}xtddddgD]`}|i|iƒƒo||iƒ|| """ % host) def serviceCapabilities (self, host, layers): xml = """ """ for name, layer in layers.items(): profile = "none" if (layer.srs == "EPSG:4326"): profile = "global-geodetic" elif (layer.srs == "OSGEO:41001"): profile = "global-mercator" xml += """ """ % (host, name, layer.srs, layer.name, profile) xml += """ """ return Capabilities("text/xml", xml) def layerCapabilities (self, host, layer): tms_type = layer.tms_type or "default" xml = """ %s %s %s """ % (host, tms_type, layer.name, layer.description, layer.srs, layer.bbox[0], layer.bbox[1], layer.bbox[2], layer.bbox[3], layer.bbox[0], layer.bbox[1], layer.size[0], layer.size[1], layer.format(), layer.extension) for z, res in enumerate(layer.resolutions): xml += """ """ % ( host, layer.name, z, res, z) xml += """ """ return Capabilities("text/xml", xml) PK˜X–7h³ðóTileCache/Services/TMS.pyc;ò ohGc@s9dklZlZdkiZdefd„ƒYZdS((sRequests CapabilitiesNsTMScBs,tZd„Zd„Zd„Zd„ZRS(Nc Csâtd„|idƒƒ}|ddj o|d}nt|ƒdjo|i|ƒSn€t|ƒdjo|i||i i ƒSnS|i |dƒ}t|ƒdjo|i ||ƒSn|didƒd|dss/iÿÿÿÿiiis.isgooglestypei(sfilterspathssplitspartsshostslensselfsserverCapabilitiessserviceCapabilitiessserviceslayerssgetLayerslayerslayerCapabilitiessNonestilestms_typesfieldsshas_keys resolutionssintsressroundsbboxssizesmaxYsLayersTile( sselfsfieldsspathshostslayersmaxYspartssresstile((s<build/bdist.darwin-8.11.1-i386/egg/TileCache/Services/TMS.pysparses$17>6cCstdd|ƒSdS(Nstext/xmls™ (s Capabilitiesshost(sselfshost((s<build/bdist.darwin-8.11.1-i386/egg/TileCache/Services/TMS.pysserverCapabilities!scCs›d}xw|iƒD]i\}}d}|idjo d}n|idjo d}n|d|||i|i|f7}qW|d7}td |ƒSdS( Nsm snones EPSG:4326sglobal-geodetics OSGEO:41001sglobal-mercators¯ s8 stext/xml( sxmlslayerssitemssnameslayersprofilessrsshosts Capabilities(sselfshostslayerssxmlslayersnamesprofile((s<build/bdist.darwin-8.11.1-i386/egg/TileCache/Services/TMS.pysserviceCapabilities's   ' cCsì|ipd}d|||i|i|i|id|id|id|id|id|id|id|id|iƒ|i f}x=t |i ƒD],\}}|d||i|||f7}q¡W|d7}td |ƒSdS( Nsdefaultsó %s %s %s iiiisn s1 stext/xml(slayerstms_typeshostsnames descriptionssrssbboxssizesformats extensionsxmls enumerates resolutionsszsress Capabilities(sselfshostslayersxmlsresstms_typesz((s<build/bdist.darwin-8.11.1-i386/egg/TileCache/Services/TMS.pyslayerCapabilities>s $ (s__name__s __module__sparsesserverCapabilitiessserviceCapabilitiesslayerCapabilities(((s<build/bdist.darwin-8.11.1-i386/egg/TileCache/Services/TMS.pysTMSs   (sTileCache.ServicesRequests CapabilitiessTileCache.LayersLayersTMS(sLayersTMSsRequests Capabilities((s<build/bdist.darwin-8.11.1-i386/egg/TileCache/Services/TMS.pys?s PK]X7Œ T¨¨TileCache/Services/WMS.pyfrom TileCache.Service import Request, Capabilities import TileCache.Layer as Layer class WMS (Request): def parse (self, fields, path, host): param = {} for key in ['bbox', 'layers', 'request', 'version']: if fields.has_key(key.upper()): param[key] = fields[key.upper()] elif fields.has_key(key): param[key] = fields[key] else: param[key] = "" if param["request"] == "GetCapabilities": return self.getCapabilities(host + path, param) else: return self.getMap(param) def getMap (self, param): bbox = map(float, param["bbox"].split(",")) layer = self.getLayer(param["layers"]) tile = layer.getTile(bbox) if not tile: raise Exception( "couldn't calculate tile index for layer %s from (%s)" % (layer.name, bbox)) return tile def getCapabilities (self, host, param): if host[-1] not in "?&": if "?" in host: host += "&" else: host += "?" metadata = self.service.metadata if "description" in metadata: description = metadata["description"] else: description = "" formats = {} for layer in self.service.layers.values(): formats[layer.format()] = 1 formats = formats.keys() xml = """ ]> OGC:WMS %s """ % (description, host) xml += """ application/vnd.ogc.wms_xml """ % (host) xml += """ """ for format in formats: xml += """ %s\n""" % format xml += """ """ % (host) xml += """ text/plain """ for name, layer in self.service.layers.items(): resolutions = " ".join(["%.9f" % r for r in layer.resolutions]) xml += """ %s %s %d %d %s %s """ % ( layer.srs, layer.srs, layer.bbox[0], layer.bbox[1], layer.bbox[2], layer.bbox[3], resolutions, layer.size[0], layer.size[1], layer.format(), name ) xml += """ """ for name, layer in self.service.layers.items(): xml += """ %s %s %s """ % ( name, layer.name, layer.srs, layer.srs, layer.bbox[0], layer.bbox[1], layer.bbox[2], layer.bbox[3]) xml += """ """ return Capabilities("text/xml", xml) PK˜X–7¥ê„HHTileCache/Services/WMS.pyc;ò ²WaGc@s9dklZlZdkiZdefd„ƒYZdS((sRequests CapabilitiesNsWMScBs#tZd„Zd„Zd„ZRS(NcCs·h}xtddddgD]`}|i|iƒƒo||iƒ|| ]> OGC:WMS %s s application/vnd.ogc.wms_xml s s% %s s s„ text/plain s s%.9fs¤ %s %s %d %d %s %s iiisÅ s %s %s %s sL stext/xml(shostsselfsservicesmetadatas descriptionsformatsslayerssvaluesslayersformatskeyssxmlsitemssnamesjoinsappends_[1]s resolutionssrssrssbboxssizes Capabilities( sselfshostsparamsxmlslayers descriptionsformatsnames_[1]srsformatss resolutionssmetadata((s<build/bdist.darwin-8.11.1-i386/egg/TileCache/Services/WMS.pysgetCapabilitiess>       7i  O (s__name__s __module__sparsesgetMapsgetCapabilities(((s<build/bdist.darwin-8.11.1-i386/egg/TileCache/Services/WMS.pysWMSs  (sTileCache.ServicesRequests CapabilitiessTileCache.LayersLayersWMS(sWMSsLayersRequests Capabilities((s<build/bdist.darwin-8.11.1-i386/egg/TileCache/Services/WMS.pys?s PKY7š“O‹‹TileCache/Services/WMTS.pyfrom TileCache.Service import Request, Capabilities, TileCacheException import TileCache.Layer as Layer class WMTS (Request): meters_per_unit = { 'degrees': 111118.752, 'meters': 1, 'feet': 0.3048 } def parse (self, fields, path, host): for key in ['scale','layer','tilerow','tilecol']: if fields.has_key(key.upper()): fields[key] = fields[key.upper()] elif not fields.has_key(key): fields[key] = "" layer = self.getLayer(fields['layer']) if not layer.units: raise TileCacheException("No units were specified on the layer. WMTS support requires units to be defined for the layer.") res = .00028 * float(fields['scale']) / self.meters_per_unit[layer.units] z = layer.getLevel(res, layer.size) tile = None maxY = int( round( (layer.bbox[3] - layer.bbox[1]) / (res * layer.size[1]) ) ) - 1 tile = Layer.Tile(layer, int(fields['tilecol']), maxY - int(fields['tilerow']), z) return tile PK˜X–78ÔåTòòTileCache/Services/WMTS.pyc;ò çXaGc@s?dklZlZlZdkiZdefd„ƒYZdS((sRequests CapabilitiessTileCacheExceptionNsWMTScBs2tZhdd<dd<dd """ for name, layer in self.service.layers.items(): if (layer.srs != "EPSG:4326"): continue xml += """ %s Layer: %s 0 %s %s %s %s false %s %s %s %s %s %s SRS:%s """ % (name, name, layer.description, float(layer.bbox[0]), float(layer.bbox[1]), float(layer.bbox[2]), float(layer.bbox[3]), layer.resolutions[0] * layer.size[0], len(layer.resolutions), layer.size[0], layer.extension, host, name, layer.srs) xml += """ """ return Capabilities("text/xml", xml) PK˜X–7Pɾ—½½ TileCache/Services/WorldWind.pyc;ò t=VGc@s9dklZlZdkiZdefd„ƒYZdS((sRequests CapabilitiesNs WorldWindcBs#tZd„Zd„Zd„ZRS(NcCsËh}xwdddddgD]`}|i|iƒƒo||iƒ|| s EPSG:4326sÀ %s Layer: %s 0 %s %s %s %s false %s %s %s %s %s %s SRS:%s iiis stext/xml(sselfsservicesmetadatas descriptionsformatsslayerssvaluesslayersformatskeyssxmlsitemssnamessrssfloatsbboxs resolutionsssizeslens extensionshosts Capabilities( sselfshostsparamsxmlslayers descriptionsnamesformatssmetadata((sBbuild/bdist.darwin-8.11.1-i386/egg/TileCache/Services/WorldWind.pysgetCapabilitiess"    ›# (s__name__s __module__sparsesgetMapsgetCapabilities(((sBbuild/bdist.darwin-8.11.1-i386/egg/TileCache/Services/WorldWind.pys WorldWinds  (sTileCache.ServicesRequests CapabilitiessTileCache.LayersLayers WorldWind(sLayersRequests Capabilitiess WorldWind((sBbuild/bdist.darwin-8.11.1-i386/egg/TileCache/Services/WorldWind.pys?s PK˜X–7“×2¤EGG-INFO/dependency_links.txtPK#S–7“×2¤<EGG-INFO/not-zip-safePK˜X–7ÕeÕÕ§L§L¤pEGG-INFO/PKG-INFOPK˜X–7¶5’’¤FMEGG-INFO/SOURCES.txtPK˜X–7»=éG ¤ SEGG-INFO/top_level.txtPK˜X–7_¼BwœœíHSEGG-INFO/scripts/tilecache.cgiPK˜X–7›’óꦦí TEGG-INFO/scripts/tilecache.fcgiPK˜X–7§øŽç ç #íUEGG-INFO/scripts/tilecache_clean.pyPK˜X–7âðŸ'')í+`EGG-INFO/scripts/tilecache_http_server.pyPK˜X–7':rP¿¿,í™aEGG-INFO/scripts/tilecache_install_config.pyPK˜X–7>õàõõ"í¢fEGG-INFO/scripts/tilecache_seed.pyPKw „7°é=A‹‹¤×gTileCache/__init__.pyPK˜X–73ˆàकhTileCache/__init__.pycPK…7/¡bVV¤©iTileCache/Cache.pyPK˜X–7Ñ:뵩 © ¤/oTileCache/Cache.pycPKw „7—zü¶¶¤ {TileCache/Client.pyPK˜X–7+[cbgg¤ð‹TileCache/Client.pycPK$B–7KJÜ»£,£,¤‰¡TileCache/Layer.pyPK˜X–7!$SÇÝ;Ý;¤\ÎTileCache/Layer.pycPK9ª’7 j}û¥.¥.¤j TileCache/Service.pyPK˜X–7/·)™P9P9¤A9TileCache/Service.pycPKw „74½~M||¤ÄrTileCache/Swarm.pyPK˜X–7„Ç´z<z<¤p’TileCache/Swarm.pycPKê’7eq±íu u ¤ÏTileCache/tilecache.cfgPK9…7¤ÅÚTileCache/Caches/__init__.pyPK˜X–7|K{{¤ÿÚTileCache/Caches/__init__.pycPK¬=‡7€‹6 „ „ ¤ÉÛTileCache/Caches/Disk.pyPK˜X–7CR¹°°¤ƒéTileCache/Caches/Disk.pycPK¬=‡7µ¦»--¤jýTileCache/Caches/Memcached.pyPK˜X–72ÐÝØ Ø ¤ÒTileCache/Caches/Memcached.pycPK…7¤æ TileCache/Layers/__init__.pyPK˜X–7uo¡¤ TileCache/Layers/__init__.pycPK…7ö\¦6Ëˤê TileCache/Layers/ArcXML.pyPK˜X–7ªV¸ŸS S ¤íTileCache/Layers/ArcXML.pycPK…7CüÜž ž ¤yTileCache/Layers/Image.pyPK˜X–7°Y`D D ¤N*TileCache/Layers/Image.pycPK¬=‡7Åà˪ª¤Ê6TileCache/Layers/Mapnik.pyPK˜X–70‚ ˆ¿ ¿ ¤¬?TileCache/Layers/Mapnik.pycPKT¸‰7+”É>;;¤¤ITileCache/Layers/MapServer.pyPK˜X–7Ë&ôeæ æ ¤QTileCache/Layers/MapServer.pycPK…7³9^³??¤<[TileCache/Layers/WMS.pyPK˜X–7xbFFWW¤°]TileCache/Layers/WMS.pycPK…7¤=cTileCache/Services/__init__.pyPK˜X–71é3à‘‘¤ycTileCache/Services/__init__.pycPK¬=‡7î.à‚ƒƒ¤GdTileCache/Services/KML.pyPK˜X–7Y’”± ± ¤mTileCache/Services/KML.pycPK[Œ…7‹uY¸¹¹¤êwTileCache/Services/MGMaps.pyPK˜X–7ªÈsÖ™™¤Ý{TileCache/Services/MGMaps.pycPKzŒ…7 ™7c  !¤±‚TileCache/Services/TileService.pyPK˜X–7ÖÄÿAA"¤ü…TileCache/Services/TileService.pycPKKª’7ã$Ì…¤}ŒTileCache/Services/TMS.pyPK˜X–7h³ðó¤ÐšTileCache/Services/TMS.pycPK]X7Œ T¨¨¤­TileCache/Services/WMS.pyPK˜X–7¥ê„HH¤íÀTileCache/Services/WMS.pycPKY7š“O‹‹¤m×TileCache/Services/WMTS.pyPK˜X–78ÔåTòò¤0ÜTileCache/Services/WMTS.pycPK…7©u‰˜n n ¤[ãTileCache/Services/WorldWind.pyPK˜X–7Pɾ—½½ ¤ñTileCache/Services/WorldWind.pycPK::\