import os from pathlib import Path import shutil import csv import re import datetime from jinja2 import Environment, PackageLoader, select_autoescape import frontmatter import markdown from markdown_include.include import MarkdownInclude from slugify import slugify markdown_include = MarkdownInclude( configs={'base_path': 'src/content/'} ) env = Environment( loader=PackageLoader("src"), autoescape=select_autoescape() ) CONTENT_D = os.path.abspath("src/content") OUTPUT_D = "dist" documents = {} def showlist(param): template = env.select_template(["snippets/show-list.jinja"]) html = template.render(documents=documents, type=param.strip()) return html def slugify_filter(value): return slugify(value) def shortcode_filter(value): shortcode_callbacks = { "showlist": showlist } def shortcode_replacer(match): shortcode_name = match.group(1).strip() param = match.group(2).strip() if shortcode_name in shortcode_callbacks: return shortcode_callbacks[shortcode_name](param) return match.group(0) pattern = re.compile(r"{{\s*(\w+)\s+([^{}]+?)\s*}}") return pattern.sub(shortcode_replacer, value) env.filters["shortcode"] = shortcode_filter env.filters["slugify"] = slugify_filter def render_single_file(template, page, path, dist): html = template.render(documents=documents, page=page) name = Path(path).stem if not os.path.exists(dist): os.makedirs(dist) with open(f"{dist}/{name}.html", "w", encoding="utf-8") as output_file: output_file.write(html) def get_page_data(path): filename = Path(path).stem page = frontmatter.load(path) page['slug'] = slugify(filename) page.filename = filename page.body = markdown.markdown(page.content, extensions=['def_list', 'footnotes', markdown_include]) return page def render_posts(path): name = Path(path).stem print(f"looking for {name}.jinja") template = env.select_template([f"{name}.jinja", "post.jinja"]) for filename in os.listdir(path): if filename.endswith(".md"): post_path = os.path.join(path, filename) page = get_page_data(post_path) render_single_file(template, page, post_path, f"{OUTPUT_D}/{name}") def preload_documents(): print("preload any needed data") for subdir in os.listdir(CONTENT_D): path = os.path.join(CONTENT_D, subdir) if os.path.isdir(path): name = Path(path).stem if name not in documents: documents[name] = [] for filename in os.listdir(path): if filename.endswith(".md"): post_path = os.path.join(path, filename) documents[name].append(get_page_data(post_path)) elif Path(path).suffix == '.md': documents[Path(path).stem] = get_page_data(path) def copy_assets(): if os.path.exists("dist/assets"): shutil.rmtree("dist/assets") shutil.copytree("src/assets", "dist/assets") def get_inventory(): with open("src/content/component-inventory.csv") as f: documents['inventory'] = [] for line in csv.DictReader(f, fieldnames=('ID', 'Name', 'Value', 'type', 'Date', 'Where')): documents['inventory'].append(line) def main(): get_inventory() preload_documents() print("render the content") for subdir in os.listdir(CONTENT_D): path = os.path.join(CONTENT_D, subdir) if os.path.isdir(path): render_posts(path) elif Path(path).suffix == '.md': template = env.select_template( [f"{Path(path).stem}.jinja", "post.jinja"]) page = get_page_data(path) render_single_file(template, page, path, OUTPUT_D) else: print("i cannot handle this file yet") copy_assets() main()