# HG changeset patch # User Tero Marttila # Date 1410707051 -10800 # Node ID 59d61da2b64f22098e482c4777ec735a3f2665a4 # Parent 79eedd96112d2c1e28b9a48cc4f3f328627b5def pngtile.tile: split off BaseAppliation diff -r 79eedd96112d -r 59d61da2b64f bin/tile-server --- a/bin/tile-server Sun Sep 14 17:23:01 2014 +0300 +++ b/bin/tile-server Sun Sep 14 18:04:11 2014 +0300 @@ -25,7 +25,7 @@ args = parser.parse_args() - application = pngtile.tile.Application( + application = pngtile.tile.TileApplication( image_root = args.image_root, ) diff -r 79eedd96112d -r 59d61da2b64f bin/tile.wsgi --- a/bin/tile.wsgi Sun Sep 14 17:23:01 2014 +0300 +++ b/bin/tile.wsgi Sun Sep 14 18:04:11 2014 +0300 @@ -1,5 +1,5 @@ import pngtile.tile -application = pngtile.tile.Application( +application = pngtile.tile.TileApplication( image_root = './var', ) diff -r 79eedd96112d -r 59d61da2b64f pngtile/application.py --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/pngtile/application.py Sun Sep 14 18:04:11 2014 +0300 @@ -0,0 +1,117 @@ +from werkzeug import Request, Response, exceptions +from werkzeug.utils import html + +import pypngtile + +import os.path + +class BaseApplication (object): + def __init__ (self, image_root): + if not os.path.isdir(image_root) : + raise Exception("Given image_root does not exist: {image_root}".format(image_root=image_root)) + + self.image_root = os.path.abspath(image_root) + + self.image_cache = { } + + def lookup_image (self, url): + """ + Lookup image by request path. + + Returns image_name, image_path. + """ + + if not os.path.isdir(self.image_root): + raise exceptions.InternalServerError("Server image_root has gone missing") + + # path to image + name = url.lstrip('/') + + # build absolute path + path = os.path.abspath(os.path.join(self.image_root, name)) + + # ensure the path points inside the data root + if not path.startswith(self.image_root): + raise exceptions.NotFound(name) + + if not os.path.exists(path): + raise exceptions.NotFound(name) + + if os.path.isdir(path): + raise exceptions.BadRequest("Is a directory: {name}".format(name=name)) + + if not path.endswith('.png'): + raise exceptions.BadRequest("Not a PNG image: {name}".format(name=name)) + + return name, path + + def get_image (self, url): + """ + Return Image object. + """ + + name, path = self.lookup_image(url) + + # get Image object + image = self.image_cache.get(path) + + if not image: + # open + image = pypngtile.Image(path) + + # check + if image.status() not in (pypngtile.CACHE_FRESH, pypngtile.CACHE_STALE): + raise exceptions.InternalServerError("Image cache not available: {name}".format(name=name)) + + # load + image.open() + + # cache + self.image_cache[path] = image + + return image, name + + def handle (self, request): + """ + Handle request for an image + """ + + raise NotImplementedError() + + @Request.application + def __call__ (self, request): + """ + WSGI entry point. + """ + + try: + return self.handle(request) + + except exceptions.HTTPException as error: + return error + + STYLESHEETS = ( ) + SCRIPTS = ( ) + + def render_html (self, title, body, stylesheets=None, scripts=None): + if stylesheets is None: + stylesheets = self.STYLESHEETS + + if scripts is None: + scripts = self.SCRIPTS + + return html.html(lang='en', *[ + html.head( + html.title(title), + *[ + html.link(rel='stylesheet', href=href) for href in stylesheets + ] + ), + html.body( + *(body + tuple( + html.script(src=src) for src in scripts + )) + ), + ]) + + diff -r 79eedd96112d -r 59d61da2b64f pngtile/tile.py --- a/pngtile/tile.py Sun Sep 14 17:23:01 2014 +0300 +++ b/pngtile/tile.py Sun Sep 14 18:04:11 2014 +0300 @@ -2,8 +2,7 @@ Raw tile handling. """ -import os.path - +from pngtile.application import BaseApplication from werkzeug import Request, Response, exceptions import pypngtile @@ -40,63 +39,10 @@ return scale(val - dim / 2, zoom) -class Application (object): - def __init__ (self, image_root): - if not os.path.isdir(image_root) : - raise Exception("Given image_root does not exist: {image_root}".format(image_root=image_root)) - - self.image_root = os.path.abspath(image_root) - - self.image_cache = { } - - def lookup_image (self, url): - """ - Lookup image by request path. - - Returns image_name, image_path. - """ - - if not os.path.isdir(self.image_root): - raise exceptions.InternalServerError("Server image_root has gone missing") - - # path to image - name = url.lstrip('/') +class TileApplication (BaseApplication): + def __init__ (self, **opts): + BaseApplication.__init__(self, **opts) - # build absolute path - path = os.path.abspath(os.path.join(self.image_root, name)) - - # ensure the path points inside the data root - if not path.startswith(self.image_root): - raise exceptions.NotFound(name) - - return name, path - - def get_image (self, url): - """ - Return Image object. - """ - - name, path = self.lookup_image(url) - - # get Image object - image = self.image_cache.get(path) - - if not image: - # open - image = pypngtile.Image(path) - - # check - if image.status() not in (pypngtile.CACHE_FRESH, pypngtile.CACHE_STALE): - raise exceptions.InternalServerError("Image cache not available: {name}".format(name=name)) - - # load - image.open() - - # cache - self.image_cache[path] = image - - return image - def render_region (self, request, image): """ Handle request for an image region @@ -147,7 +93,7 @@ """ try: - image = self.get_image(request.path) + image, name = self.get_image(request.path) except pypngtile.Error as error: raise exceptions.BadRequest(str(error)) @@ -161,16 +107,3 @@ raise exceptions.BadRequest("Unknown args") return Response(png, content_type='image/png') - - @Request.application - def __call__ (self, request): - """ - WSGI entry point. - """ - - try: - return self.handle(request) - - except exceptions.HTTPException as error: - return error -