Figured out a bunch of the views. So sleepy. master
authordsc <david.schoonover@gmail.com>
Tue, 27 Dec 2011 09:30:52 +0000 (01:30 -0800)
committerdsc <david.schoonover@gmail.com>
Tue, 27 Dec 2011 09:30:52 +0000 (01:30 -0800)
crisishaiku/templates/footer.html [new file with mode: 0644]
crisishaiku/templates/header.html [new file with mode: 0644]
crisishaiku/templates/home.html [new file with mode: 0644]
crisishaiku/templates/layout.html [new file with mode: 0644]
crisishaiku/templates/login.html [new file with mode: 0644]
crisishaiku/view/__init__.py [new file with mode: 0644]
crisishaiku/view/auth.py [moved from crisishaiku/view.py with 52% similarity]
crisishaiku/view/decorators.py [new file with mode: 0644]
crisishaiku/view/home.py [new file with mode: 0644]
crisishaiku/view/report.py [new file with mode: 0644]
todo.md [new file with mode: 0644]

diff --git a/crisishaiku/templates/footer.html b/crisishaiku/templates/footer.html
new file mode 100644 (file)
index 0000000..bbcf258
--- /dev/null
@@ -0,0 +1,3 @@
+{% block footer %}
+    <div class="copyright">&copy; Copyright 2011-2012, <a href="http://less.ly/" target="_blank">less.ly</a>.</div>
+{% endblock footer %}
diff --git a/crisishaiku/templates/header.html b/crisishaiku/templates/header.html
new file mode 100644 (file)
index 0000000..fa8498c
--- /dev/null
@@ -0,0 +1,20 @@
+{% block header %}
+    
+    <div class="auth">
+    {% if not session.logged_in %}
+        <a class="login" href="{{ url_for('login') }}">login</a>
+    {% else %}
+        <a class="logout" href="{{ url_for('logout') }}">logout</a>
+    {% endif %}
+    </div>
+    
+    {% set messages = get_flashed_messages() %}
+    {% if messages %}
+        <div class="messages">
+        {% for message in messages %}
+            <div class="flash">{{ message }}</div>
+        {% endfor %}
+        </div>
+    {% endif %}
+    
+{% endblock header %}
diff --git a/crisishaiku/templates/home.html b/crisishaiku/templates/home.html
new file mode 100644 (file)
index 0000000..5cc4945
--- /dev/null
@@ -0,0 +1,20 @@
+{% extends "layout.html" %}
+{% block title %}Home{% endblock %}
+{% block content %}
+    
+    {% if session.logged_in %}
+        <h2>hi!</h2>
+    {% endif %}
+    
+    <ul class="haikus">
+    {% for haiku in haikus %}
+        <li class="haiku">
+            <h2>{{ haiku.title }}</h2>
+            {{ haiku.text | safe }}
+        </li>
+    {% else %}
+        <li><em>Unbelievable. No haikus so far!</em></li>
+    {% endfor %}
+    </ul>
+    
+{% endblock %}
\ No newline at end of file
diff --git a/crisishaiku/templates/layout.html b/crisishaiku/templates/layout.html
new file mode 100644 (file)
index 0000000..c3e95f5
--- /dev/null
@@ -0,0 +1,20 @@
+<!doctype html>
+<html>
+<head>
+{% block head %}
+    <link rel="stylesheet" type="text/css" href="{{ url_for('static', filename='reset.min.css') }}">
+    <title>{% block title %}Welcome!{% endblock %} | CrisisHaiku</title>
+{% endblock %}
+</head>
+<body class="{{ body_classes }} {{ 'logged_in' if session.logged_in else 'not_logged_in' }}">
+    <header>
+        {% include 'header.html' %}
+    </header>
+    <div id="content">
+        {% block content %}{% endblock %}
+    </div>
+    <footer>
+        {% include 'footer.html' %}
+    </footer>
+</body>
+</html>
diff --git a/crisishaiku/templates/login.html b/crisishaiku/templates/login.html
new file mode 100644 (file)
index 0000000..e69de29
diff --git a/crisishaiku/view/__init__.py b/crisishaiku/view/__init__.py
new file mode 100644 (file)
index 0000000..1f21b36
--- /dev/null
@@ -0,0 +1,8 @@
+#!/usr/bin/env python
+# -*- coding: utf-8 -*-
+
+from . import decorators
+from .home import *
+from .auth import *
+from .report import *
+
similarity index 52%
rename from crisishaiku/view.py
rename to crisishaiku/view/auth.py
index 21363e4..4e2fe2b 100644 (file)
@@ -1,4 +1,6 @@
+#!/usr/bin/env python
 # -*- coding: utf-8 -*-
+__all__ = ('login', 'login_twitter', 'oauth_authorized', 'logout',)
 
 from flask import (
     request, session, url_for, redirect, abort, 
@@ -9,22 +11,31 @@ from crisishaiku import app, db, crypt, twitter
 from crisishaiku.model import User, Haiku, Section
 # from crisishaiku.model import User, Haiku, Section, Comment, Like, Target
 
-STATIC = path(app.root_path)/'static'
-
+from .decorators import *
 
-
-@app.route('/')
-def index():
-    return 'Hello World!'
+STATIC = path(app.root_path)/'static'
 
 
-@app.route('/favicon.ico')
-def favicon():
-    return send_from_directory(STATIC, 'favicon.ico', mimetype='image/vnd.microsoft.icon')
 
+### User Auth
 
-@app.route('/login')
+@app.route('/login', methods=['GET', 'POST'])
 def login():
+    error = None
+    if request.method == 'POST':
+        # FIXME: this is sample code
+        if request.form['username'] != 'test':
+            error = 'Invalid username'
+        elif request.form['password'] != 'loldongs':
+            error = 'Invalid password'
+        else:
+            session['logged_in'] = True
+            flash('You were logged in')
+            return redirect(url_for('home'))
+    return render_template('login.html', error=error)
+
+@app.route('/login/twitter')
+def login_twitter():
     return twitter.authorize(callback=url_for('oauth_authorized',
         next=request.args.get('next') or request.referrer or None))
 
@@ -32,7 +43,7 @@ def login():
 @app.route('/oauth-authorized')
 @twitter.authorized_handler
 def oauth_authorized(res):
-    next_url = request.args.get('next') or url_for('index')
+    next_url = request.args.get('next') or url_for('home')
     if res is None:
         flash(u'You denied the request to sign in.')
         return redirect('/login')
@@ -46,3 +57,10 @@ def oauth_authorized(res):
     flash('You were signed in as %s' % res['screen_name'])
     return redirect(next_url)
 
+
+@app.route('/logout')
+def logout():
+    session.pop('logged_in', None)
+    flash('You were logged out')
+    return redirect(url_for('home'))
+
diff --git a/crisishaiku/view/decorators.py b/crisishaiku/view/decorators.py
new file mode 100644 (file)
index 0000000..a448e0f
--- /dev/null
@@ -0,0 +1,62 @@
+#!/usr/bin/env python
+# -*- coding: utf-8 -*-
+__all__ = ('login_required', 'templated', 'cached',)
+
+from functools import wraps
+from flask import (
+    request, session, url_for, redirect, abort, 
+    render_template, g, flash, send_from_directory, )
+from path import path
+
+
+def login_required(f):
+    @wraps(f)
+    def decorated_function(*args, **kwargs):
+        if g.user is None:
+            return redirect(url_for('login', next=request.url))
+        return f(*args, **kwargs)
+    return decorated_function
+
+
+def templated(template=None):
+    def decorator(f):
+        @wraps(f)
+        def decorated_function(*args, **kwargs):
+            template_name = template
+            if template_name is None:
+                template_name = request.endpoint \
+                    .replace('.', '/') + '.html'
+            ctx = f(*args, **kwargs)
+            if ctx is None:
+                ctx = {}
+            elif not isinstance(ctx, dict):
+                return ctx
+            return render_template(template_name, **ctx)
+        return decorated_function
+    return decorator
+
+
+try:
+    from crisishaiku import cache
+    def cached(timeout=5*60, key='view/%s'):
+        def decorator(f):
+            @wraps(f)
+            def decorated_function(*args, **kwargs):
+                cache_key = key % request.path
+                rv = cache.get(cache_key)
+                if rv is not None:
+                    return rv
+                rv = f(*args, **kwargs)
+                cache.set(cache_key, rv, timeout=timeout)
+                return rv
+            return decorated_function
+        return decorator
+    
+except ImportError:
+    # from crisishaiku import app
+    # app.logger.info('Caching disabled!')
+    def identity(f): return f
+    def cached(timeout=5*60, key='view/%s'):
+        return identity
+
+
diff --git a/crisishaiku/view/home.py b/crisishaiku/view/home.py
new file mode 100644 (file)
index 0000000..1f77008
--- /dev/null
@@ -0,0 +1,27 @@
+# -*- coding: utf-8 -*-
+__all__ = ('favicon', 'home',)
+
+from flask import (
+    request, session, url_for, redirect, abort, 
+    render_template, g, flash, send_from_directory, )
+from path import path
+
+from crisishaiku import app, db, crypt, twitter
+from crisishaiku.model import User, Haiku, Section
+# from crisishaiku.model import User, Haiku, Section, Comment, Like, Target
+
+from .decorators import *
+
+STATIC = path(app.root_path)/'static'
+
+
+
+@app.route('/favicon.ico')
+def favicon():
+    return send_from_directory(STATIC, 'favicon.ico', mimetype='image/vnd.microsoft.icon')
+
+@app.route('/')
+@templated() # template inferred from endpoint function name
+def home():
+    return dict(haikus=[], body_classes='home')
+
diff --git a/crisishaiku/view/report.py b/crisishaiku/view/report.py
new file mode 100644 (file)
index 0000000..0026b97
--- /dev/null
@@ -0,0 +1,34 @@
+#!/usr/bin/env python
+# -*- coding: utf-8 -*-
+__all__ = ('report', 'report_chapter',)
+
+from flask import (
+    request, session, url_for, redirect, abort, 
+    render_template, g, flash, send_from_directory, )
+from path import path
+
+from crisishaiku import app, db, crypt, twitter
+from crisishaiku.model import User, Haiku, Section
+# from crisishaiku.model import User, Haiku, Section, Comment, Like, Target
+
+from .decorators import *
+
+STATIC = path(app.root_path)/'static'
+
+
+
+### Report pages
+
+@app.route('/report')
+@app.route('/report/toc')
+@templated() # template inferred from endpoint function name
+def report():
+    return {}
+
+@app.route('/report/<chapter>/')
+@app.route('/report/chapter/<int:chapter_num>/')
+@templated()
+def report_chapter(chapter=None, chapter_num=None):
+    return {}
+
+
diff --git a/todo.md b/todo.md
new file mode 100644 (file)
index 0000000..85dfcb7
--- /dev/null
+++ b/todo.md
@@ -0,0 +1,2 @@
+# todo
+