move qmsk_www_pages to qmsk.pages
authorTero Marttila <terom@qmsk.net>
Sat, 04 Oct 2014 13:32:59 +0300
changeset 233 f5227f26231b
parent 232 5a16a53e9800
child 234 70b425280964
move qmsk_www_pages to qmsk.pages
qmsk/pages/__init__.py
qmsk/pages/pages.py
qmsk/pages/static/qmsk.pages/pages.css
qmsk/pages/templates/qmsk.pages/error.html
qmsk/pages/templates/qmsk.pages/page.html
qmsk/pages/urls.py
qmsk/pages/views.py
qmsk_www/settings/pages.py
qmsk_www/settings/site.py
qmsk_www/templates/site.html
qmsk_www/urls.py
qmsk_www_pages/__init__.py
qmsk_www_pages/pages.py
qmsk_www_pages/static/pages/pages.css
qmsk_www_pages/templates/pages/error.html
qmsk_www_pages/templates/pages/page.html
qmsk_www_pages/urls.py
qmsk_www_pages/views.py
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/qmsk/pages/pages.py	Sat Oct 04 13:32:59 2014 +0300
@@ -0,0 +1,379 @@
+from django.conf import settings
+
+import codecs
+import datetime
+import logging; log = logging.getLogger('qmsk.pages.pages')
+import os, os.path
+
+import markdown
+import mako.template
+
+class NotFound (Exception):
+    pass
+
+class RenderError (Exception):
+    pass
+
+class Site (object):
+    @classmethod
+    def lookup (cls):
+        return cls(
+            root        = settings.QMSK_PAGES_DIR,
+            name        = settings.QMSK_PAGES_SITE,
+        )
+
+    def __init__ (self, root, name):
+        self.root = root
+        self.name = name
+
+    def tree (self):
+        return Tree(self.root, None, (), self,
+                title       = self.name,
+        )
+
+class Tree (object):
+    INDEX = 'index'
+
+    @classmethod
+    def lookup (cls, site, parts):
+        """
+            Returns Tree
+
+            Raises NotFound
+        """
+
+        parents = ( )
+        tree = site.tree()
+
+        for name in parts:
+            if name.startswith('.'):
+                # evil
+                raise NotFound()
+            
+            if not name:
+                continue
+        
+            path = os.path.join(tree.path, name)
+
+            if not os.path.exists(path):
+                raise NotFound()
+            
+            if not os.path.isdir(path):
+                raise NotFound()
+
+            # title
+            title = tree.item_title(name)
+
+            parents += (tree, )
+            tree = cls(path, name, parents, site,
+                    title   = title,
+            )
+
+        return tree
+
+    def __init__ (self, path, name, parents, site,
+            title   = None,
+    ):
+        """
+            path:       filesystem path
+            name:       subtree name, or None for root
+            parents:    (Tree)
+            site:       Site
+        """
+
+        self.path = path
+        self.name = name
+        self.parents = parents
+        self.site = site
+
+        self.title = title or name
+
+    def hierarchy (self):
+        """
+            Yield Tree.
+        """
+
+        for tree in self.parents:
+            yield tree
+
+        yield self
+
+    def url (self, tree=None, page=None):
+        path = '/'.join(tree.name for tree in self.hierarchy() if tree.name is not None)
+
+        if path:
+            path += '/'
+
+        if tree:
+            path = tree + '/'
+
+        if page:
+            path += page
+
+        return path
+
+    def scan (self):
+        """
+            Scan for files in tree.
+        """
+
+        for filename in os.listdir(self.path):
+            if filename.startswith('.'):
+                continue
+            
+            if '.' in filename:
+                file_name, file_type = filename.rsplit('.', 1)
+            else:
+                file_name = filename
+                file_type = None
+
+            if not file_name:
+                continue
+
+            path = os.path.join(self.path, filename)
+            
+            yield path, file_name, file_type
+
+    def item_title (self, name):
+        """
+            Lookup item title if exists.
+        """
+
+        title_path = os.path.join(self.path, name + '.title')
+
+        log.info("%s: %s title_path=%s", self, name, title_path)
+
+        if os.path.exists(title_path):
+            return open(title_path).read().strip()
+        else:
+            return None
+
+    def list (self):
+        """
+            Lists all Trees and Pages for this Tree.
+
+            Yields (name, url, page_type or None, title)
+        """
+        
+        for path, name, file_type in self.scan():
+            title = self.item_title(name) or name
+
+            # trees
+            if os.path.isdir(path):
+                yield name, self.url(tree=name), None, title
+
+            if name == self.INDEX:
+                continue
+            
+            # pages
+            if not file_type:
+                continue
+
+            if file_type not in TYPES:
+                continue
+
+            yield name, self.url(page=name), file_type, title
+
+    def list_sorted (self):
+        return sorted(list(self.list()))
+
+    def page (self, name):
+        """
+            Scans through tree looking for a matching page.
+            
+            Returns Page or None.
+        """
+        
+        if not name:
+            name = self.INDEX
+            title_default = self.title
+        else:
+            title_default = None
+
+        parents = self.parents + (self, )
+
+        for path, file_name, file_type in self.scan():
+            # match on name
+            if file_name == name:
+                pass
+            elif file_type and (file_name + '.' + file_type == name):
+                pass
+            else:
+                continue
+
+            # redirects?
+            if os.path.islink(path):
+                target = os.readlink(path)
+            
+                # XXX: this should be some kind of common code
+                if '.' in target:
+                    target, target_type = target.rsplit('.', 1)
+
+                log.info("%s: %s -> %s", self, name, target)
+
+                return RedirectPage(path, name, self, parents,
+                    target  = target,
+                )
+            
+            # match on type
+            if not file_type:
+                continue
+
+            page_type = TYPES.get(file_type)
+
+            if not page_type:
+                continue
+            
+            # out
+            title = self.item_title(file_name) or title_default
+
+            return page_type(path, name, self, parents,
+                title   = title,
+            )
+
+class Page (object):
+    ENCODING = 'utf-8'
+
+    @classmethod
+    def lookup (cls, site, page):
+        """
+            Returns Page.
+            
+            Raises NotFound
+        """
+        
+        log.info("page=%r", page)
+
+        if page:
+            parts = page.split('/')
+        else:
+            parts = [ ]
+            
+        if parts:
+            page_name = parts.pop(-1)
+            tree_parts = parts
+        else:
+            page_name = ''
+            tree_parts = []
+
+        # scan dir
+        tree = Tree.lookup(site, tree_parts)
+
+        # scan page
+        page = tree.page(page_name)
+
+        if not page:
+            raise NotFound()
+
+        return page
+
+    def __init__ (self, path, name, tree, parents=(), encoding=ENCODING, title=None):
+        self.path = path
+        self.name = name
+        self.tree = tree
+        self.parents = parents
+
+        self.encoding = encoding
+        self.title = title or name
+
+    def hierarchy (self):
+        """
+            Yield (Tree, name) pairs
+        """
+
+        parent = None
+
+        for tree in self.parents:
+            if parent:
+                yield parent, tree.name
+
+            parent = tree
+
+        yield parent, self.name
+
+    def url (self):
+        return self.tree.url(page=self.name)
+
+    def open (self):
+        return codecs.open(self.path, encoding=self.encoding)
+
+    def stat (self):
+        return os.stat(self.path)
+
+    def breadcrumb (self):
+        for tree in self.tree.hierarchy():
+            yield tree.url(), tree.title
+        
+        if self.name != self.tree.INDEX:
+            yield self.url(), self.title
+
+    def modified (self):
+        return datetime.datetime.utcfromtimestamp(self.stat().st_mtime)
+
+    def redirect_page (self, request):
+        return None
+    
+    def render_html (self, request):
+        raise NotImplementedError()
+
+# TODO: tree redirects
+class RedirectPage (Page):
+    def __init__ (self, path, name, tree, parents,
+            target,
+            **opts
+    ) :
+        super(RedirectPage, self).__init__(path, name, tree, parents, **opts)
+
+        self.target = target
+
+    def redirect_page (self, request):
+        return os.path.normpath(self.tree.url() + '/' + self.target)
+
+class HTML_Page (Page):
+    def render_html (self, request):
+        return self.open().read()
+
+class MarkdownPage (Page):
+    FORMAT = 'html5'
+
+    def __init__ (self, path, name, tree, parents,
+            format=FORMAT,
+            **opts
+    ) :
+        super(MarkdownPage, self).__init__(path, name, tree, parents, **opts)
+
+        self.format = format
+
+    def render_html (self, request):
+        return markdown.markdown(self.open().read(),
+            output_format   = self.format,
+        )
+
+class TemplatePage (Page):
+    def render_html (self, request):
+        """
+            Raises RenderError if !DEBUG, arbitrary error with stack trace otherwise.
+        """
+
+        try:
+            return mako.template.Template(filename=self.path).render(
+                    request = request,
+            )
+        except Exception as error:
+            if settings.DEBUG:
+                raise
+            else:
+                raise RenderError(error)
+
+SITE = Site.lookup()
+
+TYPES = {
+    'html':         HTML_Page,
+    'md':           MarkdownPage,
+    'markdown':     MarkdownPage,
+    'tmpl':         TemplatePage,
+}
+
+def page (page):
+    return Page.lookup(SITE, page)
+
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/qmsk/pages/static/qmsk.pages/pages.css	Sat Oct 04 13:32:59 2014 +0300
@@ -0,0 +1,3 @@
+li.page-tree-item i.glyphicon {
+    float: right;
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/qmsk/pages/templates/qmsk.pages/error.html	Sat Oct 04 13:32:59 2014 +0300
@@ -0,0 +1,41 @@
+{% extends "site.html" %}
+
+{% block title %}{{ site_name }} :: {{ error_title }}{%endblock %}
+
+{% block header %}
+    <h1 class="page-header-title">
+        <a href="{% url 'page' '' %}">{{ site_name }}</a>
+    </h1>
+{% endblock %}
+
+{% block nav %}
+{% for tree, tree_name in page_hierarchy %}
+    {% if not forloop.first %}
+    <hr />
+    {% endif %}
+    <ul class="nav">
+    {% for name, page, type, title in tree.list_sorted %}
+        <li class="page-tree-item{% if type %} page-tree-{{type}}{% else %} page-tree-tree{% endif %}{% if name == tree_name %} page-tree-active{% endif %}">
+            <a href="{% url 'page' page %}">
+            {% if not type %}
+                <i class="glyphicon glyphicon-chevron-right"></i>
+            {% endif %}
+                {{ title }}
+            </a>
+        </li>
+    {% endfor %}
+    </ul>
+{% endfor %}
+{% endblock %}
+
+{% block content %}
+    <h1>{{ error_title }}</h1>
+    <div class="alert alert-warning" role="alert">
+    {% if error_message %}
+        {{ error_message }}
+    {% endif %}
+    {% if error_output %}
+        <pre>{{ error_output }}</pre>
+    {% endif %}
+    </div>
+{% endblock %}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/qmsk/pages/templates/qmsk.pages/page.html	Sat Oct 04 13:32:59 2014 +0300
@@ -0,0 +1,50 @@
+{% extends "site.html" %}
+
+{% block title %}{{ site_name }} :: {{ page_title }}{% endblock %}
+
+{% block header %}
+    <h1 class="page-header-title">
+        <a href="{% url 'page' '' %}">{{ site_name }}</a>
+    </h1>
+{% endblock %}
+
+{% block breadcrumb %}
+    <ol class="breadcrumb">
+    {% for page, title in page_breadcrumb %}
+        <li><a href="{% url 'page' page %}">{{ title }}</a></li>
+    {% endfor %}
+    </ol>
+{% endblock %}
+
+{% block nav %}
+{% for tree, tree_name in page_hierarchy %}
+    {% if not forloop.first %}
+    <hr />
+    {% endif %}
+    <ul class="nav">
+    {% for name, page, type, title in tree.list_sorted %}
+        <li class="page-tree-item{% if type %} page-tree-{{type}}{% else %} page-tree-tree{% endif %}{% if name == tree_name %} page-tree-active{% endif %}">
+            <a href="{% url 'page' page %}">
+            {% if not type %}
+                <i class="glyphicon glyphicon-chevron-right"></i>
+            {% endif %}
+                {{ title }}
+            </a>
+        </li>
+    {% endfor %}
+    </ul>
+{% endfor %}
+{% endblock %}
+
+{% block content %}
+    <h1>{{ page_title }}</h1>
+
+    {{ page_html|safe }}
+{% endblock %}
+
+{% block footer %}
+    <p class="page-footer-modified">
+        Page modified <span title="{{ page_modified|date:'DATETIME_FORMAT' }}">{{ page_modified|date }}</span>
+    </p>
+{% endblock %}
+
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/qmsk/pages/urls.py	Sat Oct 04 13:32:59 2014 +0300
@@ -0,0 +1,7 @@
+from django.conf.urls import patterns, include, url
+
+from qmsk.pages import views
+
+urlpatterns = patterns('',
+    url(r'^(?P<page>.*)$',              views.page,         name='page'),
+)
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/qmsk/pages/views.py	Sat Oct 04 13:32:59 2014 +0300
@@ -0,0 +1,55 @@
+from django import http
+from django.shortcuts import render, redirect
+
+from qmsk.pages import pages
+
+def page_error (request, page, status, title, error_message=None, error_exception=None):
+    site = pages.SITE
+
+    if page:
+        page_hierarchy = list(page.hierarchy())
+    else:
+        tree = site.tree()
+        page_hierarchy = [(tree, None)]
+
+    return render(request, 'qmsk.pages/error.html', dict(
+        site_name       = site.name,
+        page_hierarchy  = page_hierarchy,
+        error_page      = page,
+        error_title     = title,
+        error_message   = error_message,
+        error_output    = str(error_exception) if error_exception else None,
+    ), status=status)
+
+# Create your views here.
+def page (request, page):
+    try:
+        page = pages.page(page)
+    except pages.NotFound as error:
+        return page_error(request, None,
+                status  = 404,
+                title   = u"Not Found",
+                error_message   = page,
+        )
+
+    redirect_page = page.redirect_page(request)
+
+    if redirect_page:
+        return redirect('page', redirect_page)
+    
+    try:
+        return render(request, 'qmsk.pages/page.html', dict(
+                site_name       = page.tree.site.name,
+                page_name       = page.name,
+                page_title      = page.title,
+                page_breadcrumb = page.breadcrumb(),
+                page_hierarchy  = list(page.hierarchy()),
+                page_html       = page.render_html(request),
+                page_modified   = page.modified(),
+        ))
+    except pages.RenderError as error:
+        return page_error(request, page,
+                status  = 500,
+                title   = u"Server Error: {page}".format(page=page.url()),
+                error_exception     = error,
+        )
--- a/qmsk_www/settings/pages.py	Sat Oct 04 13:32:35 2014 +0300
+++ b/qmsk_www/settings/pages.py	Sat Oct 04 13:32:59 2014 +0300
@@ -1,2 +1,2 @@
-QMSK_WWW_PAGES_DIR = './pages'
-QMSK_WWW_PAGES_SITE = "qmsk.net"
+QMSK_PAGES_DIR = './pages'
+QMSK_PAGES_SITE = "qmsk.net"
--- a/qmsk_www/settings/site.py	Sat Oct 04 13:32:35 2014 +0300
+++ b/qmsk_www/settings/site.py	Sat Oct 04 13:32:59 2014 +0300
@@ -2,7 +2,7 @@
 INSTALLED_APPS = (
     'django.contrib.staticfiles',
     
-    'qmsk_www_pages',
+    'qmsk.pages',
 )
 
 MIDDLEWARE_CLASSES = (
--- a/qmsk_www/templates/site.html	Sat Oct 04 13:32:35 2014 +0300
+++ b/qmsk_www/templates/site.html	Sat Oct 04 13:32:59 2014 +0300
@@ -11,7 +11,7 @@
 
         <!-- qmsk.www.pages -->
         <link rel="stylesheet" href="{% static "style.css" %}">
-        <link rel="stylesheet" href="{% static "pages/pages.css" %}">
+        <link rel="stylesheet" href="{% static "qmsk.pages/pages.css" %}">
         
         {% block head %}
 
--- a/qmsk_www/urls.py	Sat Oct 04 13:32:35 2014 +0300
+++ b/qmsk_www/urls.py	Sat Oct 04 13:32:59 2014 +0300
@@ -2,9 +2,7 @@
 
 urlpatterns = patterns('',
     # Examples:
-    # url(r'^$', 'qmsk_www.views.home', name='home'),
-    # url(r'^blog/', include('blog.urls')),
-    url(r'^',           include('qmsk_www_pages.urls')),
+    url(r'^',           include('qmsk.pages.urls')),
 )
 
 if False:
--- a/qmsk_www_pages/pages.py	Sat Oct 04 13:32:35 2014 +0300
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,379 +0,0 @@
-from django.conf import settings
-
-import codecs
-import datetime
-import logging; log = logging.getLogger('qmsk_www_pages.pages')
-import os, os.path
-
-import markdown
-import mako.template
-
-class NotFound (Exception):
-    pass
-
-class RenderError (Exception):
-    pass
-
-class Site (object):
-    @classmethod
-    def lookup (cls):
-        return cls(
-            root        = settings.QMSK_WWW_PAGES_DIR,
-            name        = settings.QMSK_WWW_PAGES_SITE,
-        )
-
-    def __init__ (self, root, name):
-        self.root = root
-        self.name = name
-
-    def tree (self):
-        return Tree(self.root, None, (), self,
-                title       = self.name,
-        )
-
-class Tree (object):
-    INDEX = 'index'
-
-    @classmethod
-    def lookup (cls, site, parts):
-        """
-            Returns Tree
-
-            Raises NotFound
-        """
-
-        parents = ( )
-        tree = site.tree()
-
-        for name in parts:
-            if name.startswith('.'):
-                # evil
-                raise NotFound()
-            
-            if not name:
-                continue
-        
-            path = os.path.join(tree.path, name)
-
-            if not os.path.exists(path):
-                raise NotFound()
-            
-            if not os.path.isdir(path):
-                raise NotFound()
-
-            # title
-            title = tree.item_title(name)
-
-            parents += (tree, )
-            tree = cls(path, name, parents, site,
-                    title   = title,
-            )
-
-        return tree
-
-    def __init__ (self, path, name, parents, site,
-            title   = None,
-    ):
-        """
-            path:       filesystem path
-            name:       subtree name, or None for root
-            parents:    (Tree)
-            site:       Site
-        """
-
-        self.path = path
-        self.name = name
-        self.parents = parents
-        self.site = site
-
-        self.title = title or name
-
-    def hierarchy (self):
-        """
-            Yield Tree.
-        """
-
-        for tree in self.parents:
-            yield tree
-
-        yield self
-
-    def url (self, tree=None, page=None):
-        path = '/'.join(tree.name for tree in self.hierarchy() if tree.name is not None)
-
-        if path:
-            path += '/'
-
-        if tree:
-            path = tree + '/'
-
-        if page:
-            path += page
-
-        return path
-
-    def scan (self):
-        """
-            Scan for files in tree.
-        """
-
-        for filename in os.listdir(self.path):
-            if filename.startswith('.'):
-                continue
-            
-            if '.' in filename:
-                file_name, file_type = filename.rsplit('.', 1)
-            else:
-                file_name = filename
-                file_type = None
-
-            if not file_name:
-                continue
-
-            path = os.path.join(self.path, filename)
-            
-            yield path, file_name, file_type
-
-    def item_title (self, name):
-        """
-            Lookup item title if exists.
-        """
-
-        title_path = os.path.join(self.path, name + '.title')
-
-        log.info("%s: %s title_path=%s", self, name, title_path)
-
-        if os.path.exists(title_path):
-            return open(title_path).read().strip()
-        else:
-            return None
-
-    def list (self):
-        """
-            Lists all Trees and Pages for this Tree.
-
-            Yields (name, url, page_type or None, title)
-        """
-        
-        for path, name, file_type in self.scan():
-            title = self.item_title(name) or name
-
-            # trees
-            if os.path.isdir(path):
-                yield name, self.url(tree=name), None, title
-
-            if name == self.INDEX:
-                continue
-            
-            # pages
-            if not file_type:
-                continue
-
-            if file_type not in TYPES:
-                continue
-
-            yield name, self.url(page=name), file_type, title
-
-    def list_sorted (self):
-        return sorted(list(self.list()))
-
-    def page (self, name):
-        """
-            Scans through tree looking for a matching page.
-            
-            Returns Page or None.
-        """
-        
-        if not name:
-            name = self.INDEX
-            title_default = self.title
-        else:
-            title_default = None
-
-        parents = self.parents + (self, )
-
-        for path, file_name, file_type in self.scan():
-            # match on name
-            if file_name == name:
-                pass
-            elif file_type and (file_name + '.' + file_type == name):
-                pass
-            else:
-                continue
-
-            # redirects?
-            if os.path.islink(path):
-                target = os.readlink(path)
-            
-                # XXX: this should be some kind of common code
-                if '.' in target:
-                    target, target_type = target.rsplit('.', 1)
-
-                log.info("%s: %s -> %s", self, name, target)
-
-                return RedirectPage(path, name, self, parents,
-                    target  = target,
-                )
-            
-            # match on type
-            if not file_type:
-                continue
-
-            page_type = TYPES.get(file_type)
-
-            if not page_type:
-                continue
-            
-            # out
-            title = self.item_title(file_name) or title_default
-
-            return page_type(path, name, self, parents,
-                title   = title,
-            )
-
-class Page (object):
-    ENCODING = 'utf-8'
-
-    @classmethod
-    def lookup (cls, site, page):
-        """
-            Returns Page.
-            
-            Raises NotFound
-        """
-        
-        log.info("page=%r", page)
-
-        if page:
-            parts = page.split('/')
-        else:
-            parts = [ ]
-            
-        if parts:
-            page_name = parts.pop(-1)
-            tree_parts = parts
-        else:
-            page_name = ''
-            tree_parts = []
-
-        # scan dir
-        tree = Tree.lookup(site, tree_parts)
-
-        # scan page
-        page = tree.page(page_name)
-
-        if not page:
-            raise NotFound()
-
-        return page
-
-    def __init__ (self, path, name, tree, parents=(), encoding=ENCODING, title=None):
-        self.path = path
-        self.name = name
-        self.tree = tree
-        self.parents = parents
-
-        self.encoding = encoding
-        self.title = title or name
-
-    def hierarchy (self):
-        """
-            Yield (Tree, name) pairs
-        """
-
-        parent = None
-
-        for tree in self.parents:
-            if parent:
-                yield parent, tree.name
-
-            parent = tree
-
-        yield parent, self.name
-
-    def url (self):
-        return self.tree.url(page=self.name)
-
-    def open (self):
-        return codecs.open(self.path, encoding=self.encoding)
-
-    def stat (self):
-        return os.stat(self.path)
-
-    def breadcrumb (self):
-        for tree in self.tree.hierarchy():
-            yield tree.url(), tree.title
-        
-        if self.name != self.tree.INDEX:
-            yield self.url(), self.title
-
-    def modified (self):
-        return datetime.datetime.utcfromtimestamp(self.stat().st_mtime)
-
-    def redirect_page (self, request):
-        return None
-    
-    def render_html (self, request):
-        raise NotImplementedError()
-
-# TODO: tree redirects
-class RedirectPage (Page):
-    def __init__ (self, path, name, tree, parents,
-            target,
-            **opts
-    ) :
-        super(RedirectPage, self).__init__(path, name, tree, parents, **opts)
-
-        self.target = target
-
-    def redirect_page (self, request):
-        return os.path.normpath(self.tree.url() + '/' + self.target)
-
-class HTML_Page (Page):
-    def render_html (self, request):
-        return self.open().read()
-
-class MarkdownPage (Page):
-    FORMAT = 'html5'
-
-    def __init__ (self, path, name, tree, parents,
-            format=FORMAT,
-            **opts
-    ) :
-        super(MarkdownPage, self).__init__(path, name, tree, parents, **opts)
-
-        self.format = format
-
-    def render_html (self, request):
-        return markdown.markdown(self.open().read(),
-            output_format   = self.format,
-        )
-
-class TemplatePage (Page):
-    def render_html (self, request):
-        """
-            Raises RenderError if !DEBUG, arbitrary error with stack trace otherwise.
-        """
-
-        try:
-            return mako.template.Template(filename=self.path).render(
-                    request = request,
-            )
-        except Exception as error:
-            if settings.DEBUG:
-                raise
-            else:
-                raise RenderError(error)
-
-SITE = Site.lookup()
-
-TYPES = {
-    'html':         HTML_Page,
-    'md':           MarkdownPage,
-    'markdown':     MarkdownPage,
-    'tmpl':         TemplatePage,
-}
-
-def page (page):
-    return Page.lookup(SITE, page)
-
--- a/qmsk_www_pages/static/pages/pages.css	Sat Oct 04 13:32:35 2014 +0300
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,3 +0,0 @@
-li.page-tree-item i.glyphicon {
-    float: right;
-}
--- a/qmsk_www_pages/templates/pages/error.html	Sat Oct 04 13:32:35 2014 +0300
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,41 +0,0 @@
-{% extends "site.html" %}
-
-{% block title %}{{ site_name }} :: {{ error_title }}{%endblock %}
-
-{% block header %}
-    <h1 class="page-header-title">
-        <a href="{% url 'page' '' %}">{{ site_name }}</a>
-    </h1>
-{% endblock %}
-
-{% block nav %}
-{% for tree, tree_name in page_hierarchy %}
-    {% if not forloop.first %}
-    <hr />
-    {% endif %}
-    <ul class="nav">
-    {% for name, page, type, title in tree.list_sorted %}
-        <li class="page-tree-item{% if type %} page-tree-{{type}}{% else %} page-tree-tree{% endif %}{% if name == tree_name %} page-tree-active{% endif %}">
-            <a href="{% url 'page' page %}">
-            {% if not type %}
-                <i class="glyphicon glyphicon-chevron-right"></i>
-            {% endif %}
-                {{ title }}
-            </a>
-        </li>
-    {% endfor %}
-    </ul>
-{% endfor %}
-{% endblock %}
-
-{% block content %}
-    <h1>{{ error_title }}</h1>
-    <div class="alert alert-warning" role="alert">
-    {% if error_message %}
-        {{ error_message }}
-    {% endif %}
-    {% if error_output %}
-        <pre>{{ error_output }}</pre>
-    {% endif %}
-    </div>
-{% endblock %}
--- a/qmsk_www_pages/templates/pages/page.html	Sat Oct 04 13:32:35 2014 +0300
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,50 +0,0 @@
-{% extends "site.html" %}
-
-{% block title %}{{ site_name }} :: {{ page_title }}{% endblock %}
-
-{% block header %}
-    <h1 class="page-header-title">
-        <a href="{% url 'page' '' %}">{{ site_name }}</a>
-    </h1>
-{% endblock %}
-
-{% block breadcrumb %}
-    <ol class="breadcrumb">
-    {% for page, title in page_breadcrumb %}
-        <li><a href="{% url 'page' page %}">{{ title }}</a></li>
-    {% endfor %}
-    </ol>
-{% endblock %}
-
-{% block nav %}
-{% for tree, tree_name in page_hierarchy %}
-    {% if not forloop.first %}
-    <hr />
-    {% endif %}
-    <ul class="nav">
-    {% for name, page, type, title in tree.list_sorted %}
-        <li class="page-tree-item{% if type %} page-tree-{{type}}{% else %} page-tree-tree{% endif %}{% if name == tree_name %} page-tree-active{% endif %}">
-            <a href="{% url 'page' page %}">
-            {% if not type %}
-                <i class="glyphicon glyphicon-chevron-right"></i>
-            {% endif %}
-                {{ title }}
-            </a>
-        </li>
-    {% endfor %}
-    </ul>
-{% endfor %}
-{% endblock %}
-
-{% block content %}
-    <h1>{{ page_title }}</h1>
-
-    {{ page_html|safe }}
-{% endblock %}
-
-{% block footer %}
-    <p class="page-footer-modified">
-        Page modified <span title="{{ page_modified|date:'DATETIME_FORMAT' }}">{{ page_modified|date }}</span>
-    </p>
-{% endblock %}
-
--- a/qmsk_www_pages/urls.py	Sat Oct 04 13:32:35 2014 +0300
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,7 +0,0 @@
-from django.conf.urls import patterns, include, url
-
-from qmsk_www_pages import views
-
-urlpatterns = patterns('',
-    url(r'^(?P<page>.*)$',              views.page,         name='page'),
-)
--- a/qmsk_www_pages/views.py	Sat Oct 04 13:32:35 2014 +0300
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,55 +0,0 @@
-from django import http
-from django.shortcuts import render, redirect
-
-from qmsk_www_pages import pages
-
-def page_error (request, page, status, title, error_message=None, error_exception=None):
-    site = pages.SITE
-
-    if page:
-        page_hierarchy = list(page.hierarchy())
-    else:
-        tree = site.tree()
-        page_hierarchy = [(tree, None)]
-
-    return render(request, 'pages/error.html', dict(
-        site_name       = site.name,
-        page_hierarchy  = page_hierarchy,
-        error_page      = page,
-        error_title     = title,
-        error_message   = error_message,
-        error_output    = str(error_exception) if error_exception else None,
-    ), status=status)
-
-# Create your views here.
-def page (request, page):
-    try:
-        page = pages.page(page)
-    except pages.NotFound as error:
-        return page_error(request, None,
-                status  = 404,
-                title   = u"Not Found",
-                error_message   = page,
-        )
-
-    redirect_page = page.redirect_page(request)
-
-    if redirect_page:
-        return redirect('page', redirect_page)
-    
-    try:
-        return render(request, 'pages/page.html', dict(
-                site_name       = page.tree.site.name,
-                page_name       = page.name,
-                page_title      = page.title,
-                page_breadcrumb = page.breadcrumb(),
-                page_hierarchy  = list(page.hierarchy()),
-                page_html       = page.render_html(request),
-                page_modified   = page.modified(),
-        ))
-    except pages.RenderError as error:
-        return page_error(request, page,
-                status  = 500,
-                title   = u"Server Error: {page}".format(page=page.url()),
-                error_exception     = error,
-        )