from flask import Flask, url_for, render_template, abort import os import json from app.config import PANDOC_LINK, PANDOC_PATH, WHITELIST_PATH from app.hash_manager import hash_file_sha512 import subprocess app = Flask(__name__) @app.context_processor def override_url_for(): return dict(url_for=dated_url_for) #TODO: make instead of datetime hash of commit def dated_url_for(endpoint, **values): if endpoint == 'static': filename = values.get('filename', None) if filename: file_path = os.path.join(app.root_path, endpoint, filename) values['q'] = int(os.stat(file_path).st_mtime) return url_for(endpoint, **values) def render_page(page): path = f'{PANDOC_PATH}/{page}' whitelist = WHITELIST_PATH with open(whitelist, 'r') as f: if page not in f.readlines(): raise Exception("Page doesn't exist!") if not os.path.exists(f'{path}'): raise Exception("Page doesn't exist!") in_filename = f'{path}/main.md' out_filename = f'{path}/render.html' os.system(f'pandoc {in_filename} --to html --mathjax --output {out_filename}') print('Creating lock file') os.system(f'echo {hash_file_sha512(in_filename)} > {out_filename}.lock') @app.route(f'/{PANDOC_LINK}/') def get_pandoc_page(page): path = f'{PANDOC_PATH}/{page}' whitelist = WHITELIST_PATH with open(whitelist, 'r') as f: if page not in f.readlines(): return 'This page does not exist' if not os.path.exists(f'{path}'): # TODO: Add 404 handler return 'This page does not exist' with open(f'{path}/config.json') as f: data = json.loads(f.read()) if not os.path.exists(f'{path}/render.html') or not os.path.exists(f'{path}/render.html.lock'): print('Rendered page or lockfile for {page} does not exist! Rendering {page}') render_page(page) else: with open(f'{path}/render.html.lock', 'r') as f: rendered_hash = f.read().strip() current_hash = hash_file_sha512(f'{path}/main.md') if rendered_hash != current_hash: print(f'CURRENT: {current_hash}, RENDERED: {rendered_hash}') print('Integrity test failed, rendering {page}!') render_page(page) template = data['template'] with open(f'{path}/render.html', 'r') as f: inserted = f.read() return render_template(template, markdown=inserted) @app.route('/') def index(): return render_template('index.html')