Creating My Own Blogging Platform
edit: I have since replaced this python/markdown system: Blogging with Emacs and Org
Today I've started working on creating a new blogging platform for my website. Previously I had my blog setup with Wordpress, but I found that I wasn't using it much, and that it provided much more than I needed.
As a minimalist, I like the idea of a barebones style platform that I can create all the features for. It should be easy to install and maintain, which means using as little packages as possible. Currently the features that I am aiming for are the following:
- index page for the blog where all the posts are listed in reverse chronological order
- a way for me to easily publish a markdown file
- a serverless backend using the AWS ecosystem
- a commenting system
For this post I will focus on the first two items.
Publishing a markdown file has two steps:
- create a new html file from a markdown file
- update contents of blog.html to include a link to the new page.
Both of these are straightforward. First I need a way convert markdown to html. Python should be able to handle this: pip install markdown
Perfect!
Then I will need to open the markdown file, read it into a string, pass it into markdown(), and finally write it into a .html file. The only information the program will need for me is the post number, which can come from a command line argument.
After this the script will have to insert a new table row (<tr>
)
element into blog.html
<tr><td><a href="posts/4.html">Creating My Own Blogging Platform </a></td><td>Thu 07/19/18</td></tr>
This needs three things: the link, the date of the post, and the title. The link will always be 'posts/<post-number>.html', so that's easy. The title can be found by looking at the first line of the .md file, and the date will be on the second line.
The outputted html needs to include a few more things. First a `<link>` tag so that all the posts can share the same style sheet:
html = '<LINK REL=StyleSheet HREF="style.css" TYPE="text/css">\n' + html
And finally a fixed header so that readers can navigate back to the index page. For this I'll create a partial file and have the script read it and paste it into the output.
header.html
<div class="header"> <form action="../blog.html"> <input type="submit" value="blog" /> </form> </div>
create-post.py
#!/usr/bin/python3 from markdown import markdown from sys import argv """ adds a new <tr> element to blog.html new row will be the first to keep reverse chronoligical order """ def add_entry_to_list(post_num) : post_num = str(post_num) md = open(post_num+'.md') header = md.readline()[3:-1] #slice omits the beginning hashes and trailing \n date = md.readline()[5:-1] md.close() html = open('../blog.html') lines = html.readlines() html.close() new_element = '<tr><td><a href="posts/'+post_num+'.html">'+header+'</a></td><td>'+date+'</td></tr>\n' i = len(lines) - 1 while i > 0 : if lines[i].strip() == new_element.strip() : print('list item already exists') return if lines[i].strip() == '<tbody>' : lines.insert(i+1,' '+4+new_element) #indent new tag properly and add to file print('new list item created') html = open('../blog.html','wt') html.writelines(lines) html.close() return i -= 1 """ reads from the markdown file (post_num).md and writes (post_num).html """ def add_entry(post_num) : try : md = open(post_num+'.md') except : print(post_num+'.md'+' does not exist!') return h = open('header.html') header = h.read() h.close() html = markdown(md.read()) html = '<LINK REL=StyleSheet HREF="style.css" TYPE="text/css">\n' + html html = header + html md.close() post = open(post_num+'.html','wt') post.write(html) post.close() print('post updated') add_entry_to_list(post_num) if __name__ == '__main__' : post_num = argv[1] add_entry(post_num)
Next up is adding some CSS. I'm all for minimalism, but plain markdown is pretty bland. Padding, a bigger font size, and a light background will made it easier on the eyes. The post title should be in the middle and images should be kept from taking the entire page up.
html { padding: 7%; background: darkgrey; } body { background: lightgrey; padding:10px; outline: solid darkslateblue 2px; } h2 { margin: auto; text-align: center; } img { display: block; width: auto; height: auto; max-width: 50%; margin: 20px auto; border-radius:8px; } p { font-size: 18px; }
For the code snippets I'll make a thin outline and give them a lighter background so that it stands out.
pre { outline: solid black 1px; background: whitesmoke; padding: 5px; }
The header should be fixed so users don't need to scroll all the way up to go back. A darker background will work well.
.header { position:fixed; top:0px; left:0px; width:100%; background:#5f5f5f; color: #CCC; padding: 10px 20px 10px 20px; font-size:25px; }
Finally the button itself needs colors, and should highlight on mouse over.
.header form { display: inline; } input { background:#5f5f5f; color:white; border: solid #5f5f5 2px; transition-duration: 0.4s; border-radius: 4px; font-size:20px; } input:hover { background:grey; color:white; border: solid #5f5f5 2px; transition-duration: 0.4s; border-radius: 4px; font-size:20px; }
A great part of markdown is that you can add any html tag whenever you need it. So my blog will be able to support whatever interactive elements I feel like making. Pretty cool!
<button id="before-after"> Before/After </button> <script> document.getElementById('before-after').addEventListener('click',function() { document.styleSheets[0].disabled = !document.styleSheets[0].disabled; document.styleSheets[1].disabled = !document.styleSheets[1].disabled; }); </script>
The style looks okay for now, but I will most likely keep tinkering with it.
EDIT: I have made significant changes since then. Here's the result of the above style Updated source code can be found here