Refactored website
This commit is contained in:
parent
ad55cb7e34
commit
857f5a8020
9 changed files with 282 additions and 272 deletions
|
|
@ -35,16 +35,16 @@ app.add_url_rule('/docs/flask-docs.pdf', endpoint='docs.pdf',
|
||||||
app.add_url_rule('/docs/flask-docs.zip', endpoint='docs.zip',
|
app.add_url_rule('/docs/flask-docs.zip', endpoint='docs.zip',
|
||||||
build_only=True)
|
build_only=True)
|
||||||
|
|
||||||
from flask_website.views.general import general
|
from flask_website.views import general
|
||||||
from flask_website.views.community import community
|
from flask_website.views import community
|
||||||
from flask_website.views.mailinglist import mailinglist
|
from flask_website.views import mailinglist
|
||||||
from flask_website.views.snippets import snippets
|
from flask_website.views import snippets
|
||||||
from flask_website.views.extensions import extensions
|
from flask_website.views import extensions
|
||||||
app.register_module(general)
|
app.register_module(general.mod)
|
||||||
app.register_module(community)
|
app.register_module(community.mod)
|
||||||
app.register_module(mailinglist)
|
app.register_module(mailinglist.mod)
|
||||||
app.register_module(snippets)
|
app.register_module(snippets.mod)
|
||||||
app.register_module(extensions)
|
app.register_module(extensions.mod)
|
||||||
|
|
||||||
from flask_website.database import User, db_session
|
from flask_website.database import User, db_session
|
||||||
from flask_website import utils
|
from flask_website import utils
|
||||||
|
|
|
||||||
0
flask_website/listings/__init__.py
Normal file
0
flask_website/listings/__init__.py
Normal file
151
flask_website/listings/extensions.py
Normal file
151
flask_website/listings/extensions.py
Normal file
|
|
@ -0,0 +1,151 @@
|
||||||
|
from urlparse import urlparse
|
||||||
|
from werkzeug import url_quote
|
||||||
|
from flask import Markup
|
||||||
|
|
||||||
|
|
||||||
|
class Extension(object):
|
||||||
|
|
||||||
|
def __init__(self, name, author, description,
|
||||||
|
github=None, bitbucket=None, docs=None, website=None):
|
||||||
|
self.name = name
|
||||||
|
self.author = author
|
||||||
|
self.description = Markup(description)
|
||||||
|
self.github = github
|
||||||
|
self.bitbucket = bitbucket
|
||||||
|
self.docs = docs
|
||||||
|
self.website = website
|
||||||
|
|
||||||
|
@property
|
||||||
|
def pypi(self):
|
||||||
|
return 'http://pypi.python.org/pypi/%s' % url_quote(self.name)
|
||||||
|
|
||||||
|
@property
|
||||||
|
def docserver(self):
|
||||||
|
if self.docs:
|
||||||
|
return urlparse(self.docs)[1]
|
||||||
|
|
||||||
|
|
||||||
|
extensions = [
|
||||||
|
Extension('Flask-OAuth', 'Armin Ronacher',
|
||||||
|
description='''
|
||||||
|
<p>Adds <a href="http://oauth.net/">OAuth</a> support to Flask.
|
||||||
|
''',
|
||||||
|
github='mitsuhiko/flask-oauth',
|
||||||
|
docs='http://packages.python.org/Flask-OAuth/'
|
||||||
|
),
|
||||||
|
Extension('Flask-OpenID', 'Armin Ronacher',
|
||||||
|
description='''
|
||||||
|
<p>Adds <a href="http://openid.net/">OpenID</a> support to Flask.
|
||||||
|
''',
|
||||||
|
github='mitsuhiko/flask-openid',
|
||||||
|
docs='http://packages.python.org/Flask-OpenID/'
|
||||||
|
),
|
||||||
|
Extension('Flask-Babel', 'Armin Ronacher',
|
||||||
|
description='''
|
||||||
|
<p>Adds i18n/l10n support to Flask, based on
|
||||||
|
<a href=http://babel.edgewall.org/>babel</a> and
|
||||||
|
<a href=http://pytz.sourceforge.net/>pytz</a>.
|
||||||
|
''',
|
||||||
|
github='mitsuhiko/flask-babel',
|
||||||
|
docs='http://packages.python.org/Flask-Babel/'
|
||||||
|
),
|
||||||
|
Extension('Flask-SQLAlchemy', 'Armin Ronacher',
|
||||||
|
description='''
|
||||||
|
<p>Adds SQLAlchemy support to Flask. Quick and easy.
|
||||||
|
''',
|
||||||
|
github='mitsuhiko/flask-sqlalchemy',
|
||||||
|
docs='http://packages.python.org/Flask-SQLAlchemy/'
|
||||||
|
),
|
||||||
|
Extension('Flask-XML-RPC', 'Matthew Frazier',
|
||||||
|
description='''
|
||||||
|
<p>Adds <a href="http://www.xmlrpc.com/">XML-RPC</a> support to Flask.
|
||||||
|
''',
|
||||||
|
bitbucket='leafstorm/flask-xml-rpc',
|
||||||
|
docs='http://packages.python.org/Flask-XML-RPC/'
|
||||||
|
),
|
||||||
|
Extension('Flask-CouchDB', 'Matthew Frazier',
|
||||||
|
description='''
|
||||||
|
<p>Adds <a href="http://couchdb.apache.org/">CouchDB</a> support to Flask.
|
||||||
|
''',
|
||||||
|
bitbucket='leafstorm/flask-couchdb',
|
||||||
|
docs='http://packages.python.org/Flask-CouchDB/'
|
||||||
|
),
|
||||||
|
Extension('Flask-Uploads', 'Matthew Frazier',
|
||||||
|
description='''
|
||||||
|
<p>Flask-Uploads allows your application to flexibly and
|
||||||
|
efficiently handle file uploading and serving the uploaded files.
|
||||||
|
You can create different sets of uploads - one for document
|
||||||
|
attachments, one for photos, etc.
|
||||||
|
''',
|
||||||
|
bitbucket='leafstorm/flask-uploads',
|
||||||
|
docs='http://packages.python.org/Flask-Uploads/'
|
||||||
|
),
|
||||||
|
Extension('Flask-Genshi', 'Dag Odenhall',
|
||||||
|
description='''
|
||||||
|
<p>Adds support for the <a href="http://genshi.edgewall.org/">Genshi</a>
|
||||||
|
templating language to Flask applications.
|
||||||
|
''',
|
||||||
|
bitbucket='dag/flask-genshi',
|
||||||
|
docs='http://packages.python.org/Flask-Genshi/'
|
||||||
|
),
|
||||||
|
Extension('flask-mail', 'Dan Jacob',
|
||||||
|
description='''
|
||||||
|
<p>Makes sending mails from Flask applications very easy and
|
||||||
|
has also support for unittesting.
|
||||||
|
''',
|
||||||
|
bitbucket='danjac/flask-mail',
|
||||||
|
docs='http://packages.python.org/flask-mail/'
|
||||||
|
),
|
||||||
|
Extension('Flask-WTF', 'Dan Jacob',
|
||||||
|
description='''
|
||||||
|
<p>Flask-WTF offers simple integration with WTForms. This
|
||||||
|
integration includes optional CSRF handling for greater security.
|
||||||
|
''',
|
||||||
|
bitbucket='danjac/flask-wtf',
|
||||||
|
docs='http://packages.python.org/Flask-WTF/'
|
||||||
|
),
|
||||||
|
Extension('Flask-Testing', 'Dan Jacob',
|
||||||
|
description='''
|
||||||
|
<p>The Flask-Testing extension provides unit testing utilities for Flask.
|
||||||
|
''',
|
||||||
|
bitbucket='danjac/flask-testing',
|
||||||
|
docs='http://packages.python.org/Flask-Testing/'
|
||||||
|
),
|
||||||
|
Extension('Flask-Script', 'Dan Jacob',
|
||||||
|
description='''
|
||||||
|
<p>The Flask-Script extension provides support for writing external
|
||||||
|
scripts in Flask. It uses argparse to parse command line arguments.
|
||||||
|
''',
|
||||||
|
bitbucket='danjac/flask-script',
|
||||||
|
docs='http://packages.python.org/Flask-Script/'
|
||||||
|
),
|
||||||
|
Extension('flask-csrf', 'Steve Losh',
|
||||||
|
description='''
|
||||||
|
<p>A small Flask extension for adding
|
||||||
|
<a href=http://en.wikipedia.org/wiki/CSRF>CSRF</a> protection.
|
||||||
|
''',
|
||||||
|
docs='http://sjl.bitbucket.org/flask-csrf/',
|
||||||
|
bitbucket='sjl/flask-csrf'
|
||||||
|
),
|
||||||
|
Extension('flask-lesscss', 'Steve Losh',
|
||||||
|
description='''
|
||||||
|
<p>
|
||||||
|
A small Flask extension that makes it easy to use
|
||||||
|
<a href=http://lesscss.org/>LessCSS</a> with your
|
||||||
|
Flask application.
|
||||||
|
''',
|
||||||
|
docs='http://sjl.bitbucket.org/flask-lesscss/',
|
||||||
|
bitbucket='sjl/flask-lesscss'
|
||||||
|
),
|
||||||
|
Extension('flask-urls', 'Steve Losh',
|
||||||
|
description='''
|
||||||
|
<p>
|
||||||
|
A collection of URL-related functions for Flask applications.
|
||||||
|
''',
|
||||||
|
docs='http://sjl.bitbucket.org/flask-urls/',
|
||||||
|
bitbucket='sjl/flask-urls'
|
||||||
|
)
|
||||||
|
]
|
||||||
|
|
||||||
|
|
||||||
|
extensions.sort(key=lambda x: x.name.lower())
|
||||||
82
flask_website/listings/projects.py
Normal file
82
flask_website/listings/projects.py
Normal file
|
|
@ -0,0 +1,82 @@
|
||||||
|
# -*- coding: utf-8 -*-
|
||||||
|
from urlparse import urlparse
|
||||||
|
from flask import Markup
|
||||||
|
|
||||||
|
|
||||||
|
class Project(object):
|
||||||
|
|
||||||
|
def __init__(self, name, url, description, source=None):
|
||||||
|
self.name = name
|
||||||
|
self.url = url
|
||||||
|
self.description = Markup(description)
|
||||||
|
self.source = source
|
||||||
|
|
||||||
|
@property
|
||||||
|
def host(self):
|
||||||
|
return urlparse(self.url)[1]
|
||||||
|
|
||||||
|
@property
|
||||||
|
def sourcehost(self):
|
||||||
|
if self.source is not None:
|
||||||
|
return urlparse(self.source)[1]
|
||||||
|
|
||||||
|
|
||||||
|
projects = {
|
||||||
|
'websites': [
|
||||||
|
Project('Flask Website', 'http://flask.pocoo.org/', '''
|
||||||
|
<p>
|
||||||
|
The website of the Flask microframework itself including the
|
||||||
|
mailinglist interface, snippet archive and extension registry.
|
||||||
|
'''),
|
||||||
|
Project('Brightonpy', 'http://brightonpy.org/', '''
|
||||||
|
<p>
|
||||||
|
The website of the Brighton Python User Group
|
||||||
|
''', source='http://github.com/j4mie/brightonpy.org/'),
|
||||||
|
Project('vlasiku.lojban.org', 'http://vlasisku.lojban.org/', '''
|
||||||
|
<p>
|
||||||
|
An intelligent search engine for the Lojban dictionary.
|
||||||
|
'''),
|
||||||
|
Project(u's h o r e … software development', 'http://shore.be/', '''
|
||||||
|
<p>Corporate website of Shore Software Development.
|
||||||
|
'''),
|
||||||
|
# this one might change URL soon, check on each update
|
||||||
|
Project('rdrei.net', 'http://new.rdrei.net/', '''
|
||||||
|
<p>Personal website of Pascal Hartig.
|
||||||
|
'''),
|
||||||
|
],
|
||||||
|
'apps': [
|
||||||
|
Project('960 Layout System', 'http://960ls.atomidata.com/', '''
|
||||||
|
<p>
|
||||||
|
The generator of the 960 Layout System is powered by Flask. It
|
||||||
|
generates downloadable 960 stylesheets.
|
||||||
|
'''),
|
||||||
|
Project('hg-review', 'http://review.stevelosh.com/', '''
|
||||||
|
<p>
|
||||||
|
hg-review is a code review system for Mercurial. It is available
|
||||||
|
GPL2 license.
|
||||||
|
''', source='http://bitbucket.org/sjl/hg-review/'),
|
||||||
|
Project('geocron', 'http://geocron.us/', '''
|
||||||
|
<p>
|
||||||
|
By combining your present location with the time of day, geocron
|
||||||
|
automates your life.
|
||||||
|
<p>
|
||||||
|
When you get to your Metro station during the commute home,
|
||||||
|
geocron can send a text message reading "Pick me up dear" to your
|
||||||
|
spouse.
|
||||||
|
'''),
|
||||||
|
Project('Cockerel', 'http://dcolish.github.com/Cockerel/', '''
|
||||||
|
<p>An Online Logic Assistent Based on Coq.
|
||||||
|
''', source='http://github.com/dcolish/Cockerel'),
|
||||||
|
Project('Ryshcate', 'http://ryshcate.leafstorm.us/', '''
|
||||||
|
<p>
|
||||||
|
Ryshcate is a Flask powered pastebin with sourcecode
|
||||||
|
available.
|
||||||
|
''', source='http://bitbucket.org/leafstorm/ryshcate/')
|
||||||
|
]
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
# order projects by name
|
||||||
|
for _category in projects.itervalues():
|
||||||
|
_category.sort(key=lambda x: x.name.lower())
|
||||||
|
del _category
|
||||||
|
|
@ -1,113 +1,35 @@
|
||||||
# -*- coding: utf-8 -*-
|
from flask import Module, render_template
|
||||||
from urlparse import urlparse
|
|
||||||
from flask import Markup, Module, render_template
|
|
||||||
from flask_website.twitter import flask_tweets
|
from flask_website.twitter import flask_tweets
|
||||||
|
from flask_website.listings.projects import projects
|
||||||
|
|
||||||
community = Module(__name__, url_prefix='/community')
|
mod = Module(__name__, url_prefix='/community')
|
||||||
|
|
||||||
|
|
||||||
class Project(object):
|
@mod.route('/')
|
||||||
|
|
||||||
def __init__(self, name, url, description, source=None):
|
|
||||||
self.name = name
|
|
||||||
self.url = url
|
|
||||||
self.description = Markup(description)
|
|
||||||
self.source = source
|
|
||||||
|
|
||||||
@property
|
|
||||||
def host(self):
|
|
||||||
return urlparse(self.url)[1]
|
|
||||||
|
|
||||||
@property
|
|
||||||
def sourcehost(self):
|
|
||||||
if self.source is not None:
|
|
||||||
return urlparse(self.source)[1]
|
|
||||||
|
|
||||||
projects = {
|
|
||||||
'websites': [
|
|
||||||
Project('Flask Website', 'http://flask.pocoo.org/', '''
|
|
||||||
<p>
|
|
||||||
The website of the Flask microframework itself including the
|
|
||||||
mailinglist interface, snippet archive and extension registry.
|
|
||||||
'''),
|
|
||||||
Project('Brightonpy', 'http://brightonpy.org/', '''
|
|
||||||
<p>
|
|
||||||
The website of the Brighton Python User Group
|
|
||||||
''', source='http://github.com/j4mie/brightonpy.org/'),
|
|
||||||
Project('vlasiku.lojban.org', 'http://vlasisku.lojban.org/', '''
|
|
||||||
<p>
|
|
||||||
An intelligent search engine for the Lojban dictionary.
|
|
||||||
'''),
|
|
||||||
Project(u's h o r e … software development', 'http://shore.be/', '''
|
|
||||||
<p>Corporate website of Shore Software Development.
|
|
||||||
'''),
|
|
||||||
# this one might change URL soon, check on each update
|
|
||||||
Project('rdrei.net', 'http://new.rdrei.net/', '''
|
|
||||||
<p>Personal website of Pascal Hartig.
|
|
||||||
'''),
|
|
||||||
],
|
|
||||||
'apps': [
|
|
||||||
Project('960 Layout System', 'http://960ls.atomidata.com/', '''
|
|
||||||
<p>
|
|
||||||
The generator of the 960 Layout System is powered by Flask. It
|
|
||||||
generates downloadable 960 stylesheets.
|
|
||||||
'''),
|
|
||||||
Project('hg-review', 'http://review.stevelosh.com/', '''
|
|
||||||
<p>
|
|
||||||
hg-review is a code review system for Mercurial. It is available
|
|
||||||
GPL2 license.
|
|
||||||
''', source='http://bitbucket.org/sjl/hg-review/'),
|
|
||||||
Project('geocron', 'http://geocron.us/', '''
|
|
||||||
<p>
|
|
||||||
By combining your present location with the time of day, geocron
|
|
||||||
automates your life.
|
|
||||||
<p>
|
|
||||||
When you get to your Metro station during the commute home,
|
|
||||||
geocron can send a text message reading "Pick me up dear" to your
|
|
||||||
spouse.
|
|
||||||
'''),
|
|
||||||
Project('Cockerel', 'http://dcolish.github.com/Cockerel/', '''
|
|
||||||
<p>An Online Logic Assistent Based on Coq.
|
|
||||||
''', source='http://github.com/dcolish/Cockerel'),
|
|
||||||
Project('Ryshcate', 'http://ryshcate.leafstorm.us/', '''
|
|
||||||
<p>
|
|
||||||
Ryshcate is a Flask powered pastebin with sourcecode
|
|
||||||
available.
|
|
||||||
''', source='http://bitbucket.org/leafstorm/ryshcate/')
|
|
||||||
]
|
|
||||||
}
|
|
||||||
|
|
||||||
# order projects by name
|
|
||||||
for _category in projects.itervalues():
|
|
||||||
_category.sort(key=lambda x: x.name.lower())
|
|
||||||
del _category
|
|
||||||
|
|
||||||
|
|
||||||
@community.route('/')
|
|
||||||
def index():
|
def index():
|
||||||
return render_template('community/index.html')
|
return render_template('community/index.html')
|
||||||
|
|
||||||
|
|
||||||
@community.route('/irc/')
|
@mod.route('/irc/')
|
||||||
def irc():
|
def irc():
|
||||||
return render_template('community/irc.html')
|
return render_template('community/irc.html')
|
||||||
|
|
||||||
|
|
||||||
@community.route('/twitter/')
|
@mod.route('/twitter/')
|
||||||
def twitter():
|
def twitter():
|
||||||
return render_template('community/twitter.html', tweets=flask_tweets)
|
return render_template('community/twitter.html', tweets=flask_tweets)
|
||||||
|
|
||||||
|
|
||||||
@community.route('/badges/')
|
@mod.route('/badges/')
|
||||||
def badges():
|
def badges():
|
||||||
return render_template('community/badges.html')
|
return render_template('community/badges.html')
|
||||||
|
|
||||||
|
|
||||||
@community.route('/poweredby/')
|
@mod.route('/poweredby/')
|
||||||
def poweredby():
|
def poweredby():
|
||||||
return render_template('community/poweredby.html', projects=projects)
|
return render_template('community/poweredby.html', projects=projects)
|
||||||
|
|
||||||
|
|
||||||
@community.route('/logos/')
|
@mod.route('/logos/')
|
||||||
def logos():
|
def logos():
|
||||||
return render_template('community/logos.html')
|
return render_template('community/logos.html')
|
||||||
|
|
|
||||||
|
|
@ -1,159 +1,14 @@
|
||||||
from urlparse import urlparse
|
from flask import Module, render_template
|
||||||
from flask import Module, render_template, Markup
|
from flask_website.listings.extensions import extensions
|
||||||
from werkzeug import url_quote
|
|
||||||
|
|
||||||
extensions = Module(__name__, url_prefix='/extensions')
|
mod = Module(__name__, url_prefix='/extensions')
|
||||||
|
|
||||||
class Extension(object):
|
|
||||||
|
|
||||||
def __init__(self, name, author, description,
|
|
||||||
github=None, bitbucket=None, docs=None, website=None):
|
|
||||||
self.name = name
|
|
||||||
self.author = author
|
|
||||||
self.description = Markup(description)
|
|
||||||
self.github = github
|
|
||||||
self.bitbucket = bitbucket
|
|
||||||
self.docs = docs
|
|
||||||
self.website = website
|
|
||||||
|
|
||||||
@property
|
|
||||||
def pypi(self):
|
|
||||||
return 'http://pypi.python.org/pypi/%s' % url_quote(self.name)
|
|
||||||
|
|
||||||
@property
|
|
||||||
def docserver(self):
|
|
||||||
if self.docs:
|
|
||||||
return urlparse(self.docs)[1]
|
|
||||||
|
|
||||||
database = [
|
|
||||||
Extension('Flask-OAuth', 'Armin Ronacher',
|
|
||||||
description='''
|
|
||||||
<p>Adds <a href="http://oauth.net/">OAuth</a> support to Flask.
|
|
||||||
''',
|
|
||||||
github='mitsuhiko/flask-oauth',
|
|
||||||
docs='http://packages.python.org/Flask-OAuth/'
|
|
||||||
),
|
|
||||||
Extension('Flask-OpenID', 'Armin Ronacher',
|
|
||||||
description='''
|
|
||||||
<p>Adds <a href="http://openid.net/">OpenID</a> support to Flask.
|
|
||||||
''',
|
|
||||||
github='mitsuhiko/flask-openid',
|
|
||||||
docs='http://packages.python.org/Flask-OpenID/'
|
|
||||||
),
|
|
||||||
Extension('Flask-Babel', 'Armin Ronacher',
|
|
||||||
description='''
|
|
||||||
<p>Adds i18n/l10n support to Flask, based on
|
|
||||||
<a href=http://babel.edgewall.org/>babel</a> and
|
|
||||||
<a href=http://pytz.sourceforge.net/>pytz</a>.
|
|
||||||
''',
|
|
||||||
github='mitsuhiko/flask-babel',
|
|
||||||
docs='http://packages.python.org/Flask-Babel/'
|
|
||||||
),
|
|
||||||
Extension('Flask-SQLAlchemy', 'Armin Ronacher',
|
|
||||||
description='''
|
|
||||||
<p>Adds SQLAlchemy support to Flask. Quick and easy.
|
|
||||||
''',
|
|
||||||
github='mitsuhiko/flask-sqlalchemy',
|
|
||||||
docs='http://packages.python.org/Flask-SQLAlchemy/'
|
|
||||||
),
|
|
||||||
Extension('Flask-XML-RPC', 'Matthew Frazier',
|
|
||||||
description='''
|
|
||||||
<p>Adds <a href="http://www.xmlrpc.com/">XML-RPC</a> support to Flask.
|
|
||||||
''',
|
|
||||||
bitbucket='leafstorm/flask-xml-rpc',
|
|
||||||
docs='http://packages.python.org/Flask-XML-RPC/'
|
|
||||||
),
|
|
||||||
Extension('Flask-CouchDB', 'Matthew Frazier',
|
|
||||||
description='''
|
|
||||||
<p>Adds <a href="http://couchdb.apache.org/">CouchDB</a> support to Flask.
|
|
||||||
''',
|
|
||||||
bitbucket='leafstorm/flask-couchdb',
|
|
||||||
docs='http://packages.python.org/Flask-CouchDB/'
|
|
||||||
),
|
|
||||||
Extension('Flask-Uploads', 'Matthew Frazier',
|
|
||||||
description='''
|
|
||||||
<p>Flask-Uploads allows your application to flexibly and
|
|
||||||
efficiently handle file uploading and serving the uploaded files.
|
|
||||||
You can create different sets of uploads - one for document
|
|
||||||
attachments, one for photos, etc.
|
|
||||||
''',
|
|
||||||
bitbucket='leafstorm/flask-uploads',
|
|
||||||
docs='http://packages.python.org/Flask-Uploads/'
|
|
||||||
),
|
|
||||||
Extension('Flask-Genshi', 'Dag Odenhall',
|
|
||||||
description='''
|
|
||||||
<p>Adds support for the <a href="http://genshi.edgewall.org/">Genshi</a>
|
|
||||||
templating language to Flask applications.
|
|
||||||
''',
|
|
||||||
bitbucket='dag/flask-genshi',
|
|
||||||
docs='http://packages.python.org/Flask-Genshi/'
|
|
||||||
),
|
|
||||||
Extension('flask-mail', 'Dan Jacob',
|
|
||||||
description='''
|
|
||||||
<p>Makes sending mails from Flask applications very easy and
|
|
||||||
has also support for unittesting.
|
|
||||||
''',
|
|
||||||
bitbucket='danjac/flask-mail',
|
|
||||||
docs='http://packages.python.org/flask-mail/'
|
|
||||||
),
|
|
||||||
Extension('Flask-WTF', 'Dan Jacob',
|
|
||||||
description='''
|
|
||||||
<p>Flask-WTF offers simple integration with WTForms. This
|
|
||||||
integration includes optional CSRF handling for greater security.
|
|
||||||
''',
|
|
||||||
bitbucket='danjac/flask-wtf',
|
|
||||||
docs='http://packages.python.org/Flask-WTF/'
|
|
||||||
),
|
|
||||||
Extension('Flask-Testing', 'Dan Jacob',
|
|
||||||
description='''
|
|
||||||
<p>The Flask-Testing extension provides unit testing utilities for Flask.
|
|
||||||
''',
|
|
||||||
bitbucket='danjac/flask-testing',
|
|
||||||
docs='http://packages.python.org/Flask-Testing/'
|
|
||||||
),
|
|
||||||
Extension('Flask-Script', 'Dan Jacob',
|
|
||||||
description='''
|
|
||||||
<p>The Flask-Script extension provides support for writing external
|
|
||||||
scripts in Flask. It uses argparse to parse command line arguments.
|
|
||||||
''',
|
|
||||||
bitbucket='danjac/flask-script',
|
|
||||||
docs='http://packages.python.org/Flask-Script/'
|
|
||||||
),
|
|
||||||
Extension('flask-csrf', 'Steve Losh',
|
|
||||||
description='''
|
|
||||||
<p>A small Flask extension for adding
|
|
||||||
<a href=http://en.wikipedia.org/wiki/CSRF>CSRF</a> protection.
|
|
||||||
''',
|
|
||||||
docs='http://sjl.bitbucket.org/flask-csrf/',
|
|
||||||
bitbucket='sjl/flask-csrf'
|
|
||||||
),
|
|
||||||
Extension('flask-lesscss', 'Steve Losh',
|
|
||||||
description='''
|
|
||||||
<p>
|
|
||||||
A small Flask extension that makes it easy to use
|
|
||||||
<a href=http://lesscss.org/>LessCSS</a> with your
|
|
||||||
Flask application.
|
|
||||||
''',
|
|
||||||
docs='http://sjl.bitbucket.org/flask-lesscss/',
|
|
||||||
bitbucket='sjl/flask-lesscss'
|
|
||||||
),
|
|
||||||
Extension('flask-urls', 'Steve Losh',
|
|
||||||
description='''
|
|
||||||
<p>
|
|
||||||
A collection of URL-related functions for Flask applications.
|
|
||||||
''',
|
|
||||||
docs='http://sjl.bitbucket.org/flask-urls/',
|
|
||||||
bitbucket='sjl/flask-urls'
|
|
||||||
)
|
|
||||||
]
|
|
||||||
database.sort(key=lambda x: x.name.lower())
|
|
||||||
|
|
||||||
|
|
||||||
@extensions.route('/')
|
@mod.route('/')
|
||||||
def index():
|
def index():
|
||||||
return render_template('extensions/index.html', extensions=database)
|
return render_template('extensions/index.html', extensions=extensions)
|
||||||
|
|
||||||
|
|
||||||
@extensions.route('/creating/')
|
@mod.route('/creating/')
|
||||||
def creating():
|
def creating():
|
||||||
return render_template('extensions/creating.html')
|
return render_template('extensions/creating.html')
|
||||||
|
|
|
||||||
|
|
@ -6,15 +6,15 @@ from flask_website.twitter import flask_tweets
|
||||||
from flask_website.utils import requires_login
|
from flask_website.utils import requires_login
|
||||||
from flask_website.database import db_session, User
|
from flask_website.database import db_session, User
|
||||||
|
|
||||||
general = Module(__name__)
|
mod = Module(__name__)
|
||||||
|
|
||||||
|
|
||||||
@general.route('/')
|
@mod.route('/')
|
||||||
def index():
|
def index():
|
||||||
return render_template('general/index.html', tweets=flask_tweets)
|
return render_template('general/index.html', tweets=flask_tweets)
|
||||||
|
|
||||||
|
|
||||||
@general.route('/logout/')
|
@mod.route('/logout/')
|
||||||
def logout():
|
def logout():
|
||||||
if 'openid' in session:
|
if 'openid' in session:
|
||||||
flash(u'Logged out')
|
flash(u'Logged out')
|
||||||
|
|
@ -22,7 +22,7 @@ def logout():
|
||||||
return redirect(request.referrer or url_for('general.index'))
|
return redirect(request.referrer or url_for('general.index'))
|
||||||
|
|
||||||
|
|
||||||
@general.route('/login/', methods=['GET', 'POST'])
|
@mod.route('/login/', methods=['GET', 'POST'])
|
||||||
@oid.loginhandler
|
@oid.loginhandler
|
||||||
def login():
|
def login():
|
||||||
if g.user is not None:
|
if g.user is not None:
|
||||||
|
|
@ -41,7 +41,7 @@ def login():
|
||||||
return render_template('general/login.html', next=oid.get_next_url())
|
return render_template('general/login.html', next=oid.get_next_url())
|
||||||
|
|
||||||
|
|
||||||
@general.route('/first-login/', methods=['GET', 'POST'])
|
@mod.route('/first-login/', methods=['GET', 'POST'])
|
||||||
def first_login():
|
def first_login():
|
||||||
if g.user is not None or 'openid' not in session:
|
if g.user is not None or 'openid' not in session:
|
||||||
return redirect(url_for('login'))
|
return redirect(url_for('login'))
|
||||||
|
|
@ -59,7 +59,7 @@ def first_login():
|
||||||
openid=session['openid'])
|
openid=session['openid'])
|
||||||
|
|
||||||
|
|
||||||
@general.route('/profile/', methods=['GET', 'POST'])
|
@mod.route('/profile/', methods=['GET', 'POST'])
|
||||||
@requires_login
|
@requires_login
|
||||||
def profile():
|
def profile():
|
||||||
name = g.user.name
|
name = g.user.name
|
||||||
|
|
@ -75,7 +75,7 @@ def profile():
|
||||||
return render_template('general/profile.html', name=name)
|
return render_template('general/profile.html', name=name)
|
||||||
|
|
||||||
|
|
||||||
@general.route('/profile/change-openid/', methods=['GET', 'POST'])
|
@mod.route('/profile/change-openid/', methods=['GET', 'POST'])
|
||||||
@requires_login
|
@requires_login
|
||||||
@oid.loginhandler
|
@oid.loginhandler
|
||||||
def change_openid():
|
def change_openid():
|
||||||
|
|
|
||||||
|
|
@ -8,7 +8,7 @@ from flask import Module, render_template, json, url_for, abort, Markup
|
||||||
from flask_website.utils import split_lines_wrapping
|
from flask_website.utils import split_lines_wrapping
|
||||||
from flask_website import config
|
from flask_website import config
|
||||||
|
|
||||||
mailinglist = Module(__name__, url_prefix='/mailinglist')
|
mod = Module(__name__, url_prefix='/mailinglist')
|
||||||
|
|
||||||
|
|
||||||
class Mail(object):
|
class Mail(object):
|
||||||
|
|
@ -73,13 +73,13 @@ class Thread(object):
|
||||||
slug=self.slug)
|
slug=self.slug)
|
||||||
|
|
||||||
|
|
||||||
@mailinglist.route('/')
|
@mod.route('/')
|
||||||
def index():
|
def index():
|
||||||
return render_template('mailinglist/index.html')
|
return render_template('mailinglist/index.html')
|
||||||
|
|
||||||
|
|
||||||
@mailinglist.route('/archive/', defaults={'page': 1})
|
@mod.route('/archive/', defaults={'page': 1})
|
||||||
@mailinglist.route('/archive/page/<int:page>/')
|
@mod.route('/archive/page/<int:page>/')
|
||||||
def archive(page):
|
def archive(page):
|
||||||
all_threads = Thread.get_list()
|
all_threads = Thread.get_list()
|
||||||
offset = (page - 1) * config.THREADS_PER_PAGE
|
offset = (page - 1) * config.THREADS_PER_PAGE
|
||||||
|
|
@ -91,7 +91,7 @@ def archive(page):
|
||||||
page_count=page_count, page=page, threads=threads)
|
page_count=page_count, page=page, threads=threads)
|
||||||
|
|
||||||
|
|
||||||
@mailinglist.route('/archive/<int:year>/<int:month>/<int:day>/<slug>/')
|
@mod.route('/archive/<int:year>/<int:month>/<int:day>/<slug>/')
|
||||||
def show_thread(year, month, day, slug):
|
def show_thread(year, month, day, slug):
|
||||||
thread = Thread.get(year, month, day, slug)
|
thread = Thread.get(year, month, day, slug)
|
||||||
if thread is None:
|
if thread is None:
|
||||||
|
|
|
||||||
|
|
@ -6,17 +6,17 @@ from werkzeug.contrib.atom import AtomFeed
|
||||||
from flask_website.utils import requires_login, requires_admin, format_creole
|
from flask_website.utils import requires_login, requires_admin, format_creole
|
||||||
from flask_website.database import Category, Snippet, Comment, db_session
|
from flask_website.database import Category, Snippet, Comment, db_session
|
||||||
|
|
||||||
snippets = Module(__name__, url_prefix='/snippets')
|
mod = Module(__name__, url_prefix='/snippets')
|
||||||
|
|
||||||
|
|
||||||
@snippets.route('/')
|
@mod.route('/')
|
||||||
def index():
|
def index():
|
||||||
return render_template('snippets/index.html',
|
return render_template('snippets/index.html',
|
||||||
categories=Category.query.order_by(Category.name).all(),
|
categories=Category.query.order_by(Category.name).all(),
|
||||||
recent=Snippet.query.order_by(Snippet.pub_date.desc()).limit(5).all())
|
recent=Snippet.query.order_by(Snippet.pub_date.desc()).limit(5).all())
|
||||||
|
|
||||||
|
|
||||||
@snippets.route('/new/', methods=['GET', 'POST'])
|
@mod.route('/new/', methods=['GET', 'POST'])
|
||||||
@requires_login
|
@requires_login
|
||||||
def new():
|
def new():
|
||||||
category_id = None
|
category_id = None
|
||||||
|
|
@ -47,7 +47,7 @@ def new():
|
||||||
active_category=category_id, preview=preview)
|
active_category=category_id, preview=preview)
|
||||||
|
|
||||||
|
|
||||||
@snippets.route('/<int:id>/', methods=['GET', 'POST'])
|
@mod.route('/<int:id>/', methods=['GET', 'POST'])
|
||||||
def show(id):
|
def show(id):
|
||||||
snippet = Snippet.query.get(id)
|
snippet = Snippet.query.get(id)
|
||||||
if snippet is None:
|
if snippet is None:
|
||||||
|
|
@ -63,7 +63,7 @@ def show(id):
|
||||||
return render_template('snippets/show.html', snippet=snippet)
|
return render_template('snippets/show.html', snippet=snippet)
|
||||||
|
|
||||||
|
|
||||||
@snippets.route('/comments/<int:id>/', methods=['GET', 'POST'])
|
@mod.route('/comments/<int:id>/', methods=['GET', 'POST'])
|
||||||
@requires_admin
|
@requires_admin
|
||||||
def edit_comment(id):
|
def edit_comment(id):
|
||||||
comment = Comment.query.get(id)
|
comment = Comment.query.get(id)
|
||||||
|
|
@ -92,7 +92,7 @@ def edit_comment(id):
|
||||||
comment=comment)
|
comment=comment)
|
||||||
|
|
||||||
|
|
||||||
@snippets.route('/edit/<int:id>/', methods=['GET', 'POST'])
|
@mod.route('/edit/<int:id>/', methods=['GET', 'POST'])
|
||||||
@requires_login
|
@requires_login
|
||||||
def edit(id):
|
def edit(id):
|
||||||
snippet = Snippet.query.get(id)
|
snippet = Snippet.query.get(id)
|
||||||
|
|
@ -134,7 +134,7 @@ def edit(id):
|
||||||
categories=Category.query.order_by(Category.name).all())
|
categories=Category.query.order_by(Category.name).all())
|
||||||
|
|
||||||
|
|
||||||
@snippets.route('/category/<slug>/')
|
@mod.route('/category/<slug>/')
|
||||||
def category(slug):
|
def category(slug):
|
||||||
category = Category.query.filter_by(slug=slug).first()
|
category = Category.query.filter_by(slug=slug).first()
|
||||||
if category is None:
|
if category is None:
|
||||||
|
|
@ -144,7 +144,7 @@ def category(slug):
|
||||||
snippets=snippets)
|
snippets=snippets)
|
||||||
|
|
||||||
|
|
||||||
@snippets.route('/manage-categories/', methods=['GET', 'POST'])
|
@mod.route('/manage-categories/', methods=['GET', 'POST'])
|
||||||
@requires_admin
|
@requires_admin
|
||||||
def manage_categories():
|
def manage_categories():
|
||||||
categories = Category.query.order_by(Category.name).all()
|
categories = Category.query.order_by(Category.name).all()
|
||||||
|
|
@ -159,7 +159,7 @@ def manage_categories():
|
||||||
categories=categories)
|
categories=categories)
|
||||||
|
|
||||||
|
|
||||||
@snippets.route('/new-category/', methods=['POST'])
|
@mod.route('/new-category/', methods=['POST'])
|
||||||
@requires_admin
|
@requires_admin
|
||||||
def new_category():
|
def new_category():
|
||||||
category = Category(name=request.form['name'])
|
category = Category(name=request.form['name'])
|
||||||
|
|
@ -169,7 +169,7 @@ def new_category():
|
||||||
return redirect(url_for('manage_categories'))
|
return redirect(url_for('manage_categories'))
|
||||||
|
|
||||||
|
|
||||||
@snippets.route('/delete-category/<int:id>/', methods=['GET', 'POST'])
|
@mod.route('/delete-category/<int:id>/', methods=['GET', 'POST'])
|
||||||
@requires_admin
|
@requires_admin
|
||||||
def delete_category(id):
|
def delete_category(id):
|
||||||
category = Category.query.get(id)
|
category = Category.query.get(id)
|
||||||
|
|
@ -202,7 +202,7 @@ def delete_category(id):
|
||||||
.filter(Category.id != category.id).all())
|
.filter(Category.id != category.id).all())
|
||||||
|
|
||||||
|
|
||||||
@snippets.route('/recent.atom')
|
@mod.route('/recent.atom')
|
||||||
def recent_feed():
|
def recent_feed():
|
||||||
feed = AtomFeed(u'Recent Flask Snippets',
|
feed = AtomFeed(u'Recent Flask Snippets',
|
||||||
subtitle=u'Recent additions to the Flask snippet archive',
|
subtitle=u'Recent additions to the Flask snippet archive',
|
||||||
|
|
@ -216,7 +216,7 @@ def recent_feed():
|
||||||
return feed.get_response()
|
return feed.get_response()
|
||||||
|
|
||||||
|
|
||||||
@snippets.route('/snippets/<int:id>/comments.atom')
|
@mod.route('/snippets/<int:id>/comments.atom')
|
||||||
def comments_feed(id):
|
def comments_feed(id):
|
||||||
snippet = Snippet.query.get(id)
|
snippet = Snippet.query.get(id)
|
||||||
if snippet is None:
|
if snippet is None:
|
||||||
|
|
|
||||||
Loading…
Add table
Add a link
Reference in a new issue