Skip to content

Instantly share code, notes, and snippets.

@saviour123
Created December 21, 2016 15:07
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save saviour123/b594991af897dfb6fbd698c2cec3dba5 to your computer and use it in GitHub Desktop.
Save saviour123/b594991af897dfb6fbd698c2cec3dba5 to your computer and use it in GitHub Desktop.
Simple Static blog generator.
from flask import Flask, render_template, flash, url_for
import markdown
import os
from werkzeug import cached_property
from flask_flatpages import FlatPages
import yaml
DEBUG = True
FLATPAGES_AUTO_RELOAD = DEBUG
POSTS_FILE_EXTENSION = '.md'
app = Flask(__name__)
app.secret_key = 'saviour123'
class Blog(object):
"""docstring for Blog"""
def __init__(self, app, root_dir='', file_ext=POSTS_FILE_EXTENSION):
self.root_dir = root_dir
self.file_ext = file_ext
self._app = app
self._cache = {}
self._initialize_cache()
@property
def posts(self):
return self._cache.values()
def get_post_or_404(self, path):
"""Return a path or return 404"""
try:
return self._cache[path]
except KeyError:
abort(404)
def _initialize_cache(self):
"""loop through root_dir and creats a cache of posts"""
for (root, dirpaths, filepaths) in os.walk(self.root_dir):
for filepath in filepaths:
filename, ext = os.path.splitext(filepath)
if ext == self.file_ext:
path = os.path.join(root, filepath).replace(self.root_dir, '')
post = Post(path, root_dir=self.root_dir)
self._cache[post.urlpath] = post
#markdown rendering class
class Post(object):
def __init__(self, path, root_dir=''):
self.urlpath = os.path.splitext(path.strip('/'))[0]
self.filepath = os.path.join(root_dir, path.strip('/'))
self._initialize_metadata()
#handles the markdown conversion
@cached_property
def html(self):
with open(self.filepath, 'r') as fin:
content = fin.read().split('\r\n\r\n', 1)[1].strip() #for linux \n\n
print content
return markdown.markdown(content)
#handling of urls for clicking
@property
def url(self):
print self.urlpath
return url_for('post', path=self.urlpath)
#handle the metadata aspect
def _initialize_metadata(self):
content = ''
with open(self.filepath, 'r') as fin:
for line in fin:
if not line.strip():
break
content += line
self.__dict__.update(yaml.load(content))
blog = Blog(app, root_dir='posts')
#the data formating function
@app.template_filter('date')
def format_date(value, format='%B %d, %Y'):
return value.strftime(format)
#home route for listing
@app.route('/')
def index():
posts = [Post('hello.md', root_dir='posts')]
return render_template('index.html', posts=posts)
#blog rendering
@app.route('/blog/<path:path>/')
def post(path):
#path = os.path.join('posts', path)
#post = Post(path + POSTS_FILE_EXTENSION)
post = blog.get_post_or_404(path)
return render_template('post.html', post=post)
if __name__=='__main__':
app.run()
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment