A mirror of my website's source code.

By using this site, you agree to have cookies stored on your device, strictly for functional purposes, such as storing your session and preferences.

Dismiss

 build.py

View raw Download
text/x-script.python • 9.35 kiB
Python script, ASCII text executable
        
            
1
from Renderers import RenderTemplate, RenderMarkdown
2
from sys import argv
3
from shutil import rmtree as DeleteDirectory
4
from os import mkdir as CreateDirectory, listdir as ListDirectory, unlink as DeleteFile
5
from os.path import isfile as IsFile, exists as PathExists
6
from distutils.dir_util import copy_tree as CopyDirectory
7
from datetime import datetime
8
from json import dump as DumpJSON
9
from yaml import safe_load as LoadYML
10
from re import sub as RegReplace
11
12
GITHUB_BUILD_DIR = "docs" # Separate because this site is built with an action that won't work if they aren't
13
LOCAL_BUILD_DIR = "build"
14
15
BUILD_DIRECTORY = GITHUB_BUILD_DIR if len(argv) > 1 and argv[1] == "gh-pages-deploy" else LOCAL_BUILD_DIR
16
17
PAGES = {
18
"index.html": "index.html",
19
"blog-list.html": "blog/index.html",
20
"blog-feed.rss": "blog/feed.rss",
21
"blog-feed.atom": "blog/feed.atom",
22
"404.html": "404.html",
23
}
24
25
DISALLOWED_SITEMAP = {
26
"404.html",
27
"blog-feed.rss",
28
"blog-feed.atom",
29
"blog-list.html",
30
}
31
32
REDIRECTS = {
33
"link-tree.html": "list/link-tree.html", # Old location -> new location
34
}
35
36
SITEMAP_HREF = "https://steve0greatness.github.io/"
37
sitemap = [
38
SITEMAP_HREF + "blog/"
39
]
40
41
def WipeFinalDir():
42
if not PathExists(BUILD_DIRECTORY):
43
print("Directory didn't existing, creating it...")
44
CreateDirectory(BUILD_DIRECTORY)
45
return
46
print("Directory exists, wiping it...")
47
for item in ListDirectory(BUILD_DIRECTORY):
48
path = BUILD_DIRECTORY + "/" + item
49
if IsFile(path):
50
DeleteFile(path)
51
continue
52
DeleteDirectory(path)
53
54
def PostDateToDateObj(Date):
55
return datetime.strptime(Date, "%Y %b %d")
56
57
def PostSortHelper(Post):
58
return PostDateToDateObj(Post["date"])
59
60
def GetBlogList():
61
print("Grabbing post list")
62
PostSlugs = ListDirectory("blog-posts")
63
Posts = []
64
for slug in PostSlugs:
65
print("Grabbing post list blog-posts/%s" % (slug))
66
with open("blog-posts/" + slug, encoding="utf-8") as MDFile:
67
RawMD = MDFile.read()
68
PostHTML = RenderMarkdown(RawMD)
69
Item = PostHTML.metadata
70
Item["content"] = PostHTML
71
Item["raw-content"] = RawMD
72
Item["rss-content"] = PostHTML.replace("&", "&amp;").replace(">", "&gt;").replace("<", "&lt;")
73
Item["atom-content"] = RegReplace("</(?=.*)", "</xhtml:", RegReplace("<(?=[^\/].*)", "<xhtml:", PostHTML))
74
Item["rss-post-time"] = PostDateToDateObj(Item["date"]).strftime("%a, %d %b %Y") + " 00:00:00 GMT"
75
Item["atom-post-time"] = PostDateToDateObj(Item["date"]).strftime("%Y-%m-%d") + "T00:00:00Z"
76
Item["atom-update-time"] = Item["atom-post-time"]
77
if "updated" in Item:
78
Item["atom-update-time"] = PostDateToDateObj(Item["updated"]).strftime("%Y-%m-%d") + "T00:00:00Z"
79
Item["pathname"] = slug.replace(".md", ".html")
80
Item["plaintext"] = slug.replace(".md", ".txt")
81
Item["origin"] = slug
82
Posts.append(Item)
83
PostsByDate = sorted(Posts, key=PostSortHelper, reverse=True)
84
return PostsByDate
85
86
PostList = []
87
88
89
def ListParseCategory(Obj, depth):
90
html = "<h%d id=\"%s\">%s</h%d>" % (2+depth, Obj["id"], Obj["title"], 2+depth)
91
if "paragraph" in Obj:
92
html += "<p>%s</p>" % Obj["paragraph"]
93
listType = "ul"
94
if "list-type" in Obj and Obj["list-type"] == "ordered":
95
listType = "ol"
96
html += "<%s>" % listType
97
for item in Obj["list"]:
98
html += "<li>" + LIST_PARSER_DICT[item["type"]](item, depth + 1) + "</li>"
99
html += "</%s>" % listType
100
return html
101
102
def ListParseLink(Obj, depth):
103
html = "<a href=\"%s\">" % Obj["href"]
104
text = Obj["text"]
105
if "text-type" in Obj and Obj["text-type"] == "text/markdown":
106
text = RenderMarkdown(text).replace("<p>", "").replace("</p>", "")
107
html += text + "</a>"
108
if "comment" in Obj:
109
html += "(%s)" % Obj["comment"]
110
return html
111
112
def ListParseText(Obj, depth):
113
text = Obj["text"]
114
# if "text-type" in Obj and Obj["text-type"] == "text/markdown":
115
# print(RenderMarkdown(text))
116
# text = RenderMarkdown(text) # this doesn't work???
117
if "comment" in Obj:
118
text += "(%s)" % Obj["comment"]
119
return text
120
121
LIST_PARSER_DICT = {
122
"category": ListParseCategory,
123
"link": ListParseLink,
124
"text": ListParseText,
125
}
126
127
def GetLists():
128
ListSlugs = ListDirectory("lists")
129
Lists = []
130
for slug in ListSlugs:
131
List = {
132
"title": "",
133
"content": "",
134
"filename": slug
135
}
136
with open("lists/" + slug) as ListYML:
137
ListDict = LoadYML(ListYML.read())
138
List["title"] = ListDict["title"]
139
if "paragraph" in ListDict:
140
List["content"] += "<p>%s</p>" % ListDict["paragraph"]
141
for item in ListDict["list"]:
142
List["content"] += LIST_PARSER_DICT[item["type"]](item, 0)
143
Lists.append(List)
144
sitemap.append(SITEMAP_HREF + "list/" + slug)
145
sitemap.append(SITEMAP_HREF + "list")
146
return Lists
147
148
def RenderPosts():
149
global PostList
150
for post in PostList:
151
Revised = post["updated"] if "updated" in post else False
152
RenderedHTML = RenderTemplate("blog-post.html",
153
Revised=Revised,
154
Title=post["title"],
155
PostDate=post["date"],
156
Content=post["content"],
157
PostPath=post["pathname"],
158
PlaintextPath=post["plaintext"])
159
print("Building blog-posts/%s to %s/blog/%s" % (post["origin"], BUILD_DIRECTORY, post["pathname"]))
160
with open(BUILD_DIRECTORY + "/blog/" + post["pathname"], "w", encoding="utf-8") as PostHTMLFile:
161
PostHTMLFile.write(RenderedHTML)
162
print("Copying blog-posts/%s to %s/blog/%s" % (post["origin"], BUILD_DIRECTORY, post["plaintext"]))
163
with open(BUILD_DIRECTORY + "/blog/" + post["plaintext"], "w", encoding="utf-8") as PostHTMLFile:
164
PostHTMLFile.write(post["raw-content"])
165
sitemap.append(SITEMAP_HREF + "blog/" + post["pathname"])
166
167
def RenderPage(PageInput: str, ContentDest: str, AllowSitemap: bool = True, **kwargs):
168
print("Building views/%s to %s/%s" % (PageInput, BUILD_DIRECTORY, ContentDest))
169
if AllowSitemap:
170
sitemap.append(SITEMAP_HREF + ContentDest)
171
with open(BUILD_DIRECTORY + "/" + ContentDest, "w", encoding="utf-8") as DestLocation:
172
DestLocation.write(RenderTemplate(PageInput, **kwargs))
173
174
def CreateJSONFeed():
175
global PostList
176
CreatedJSON = {
177
"version": "https://jsonfeed.org/version/1",
178
"title": "Steve0Greatness' Blog",
179
"home_page_url": "https://steve0greatness.github.io",
180
"feed_url": "https://steve0greatness.github.io/blog/feed.rss",
181
"language": "en-US",
182
"favicon": "https://steve0greatness.github.io/favicon.ico",
183
"description": "A blog by a human being.",
184
"authors": [
185
{
186
"name": "Steve0Greatness",
187
"url": "https://steve0greatness.github.io"
188
}
189
],
190
"items": []
191
}
192
for post in PostList:
193
CreatedJSON["items"].append({
194
"id": "https://steve0greatness.github.io/blog/" + post["pathname"],
195
"title": "JSON Feed version 1.1",
196
"icon": "https://steve0greatness.github.io/favicon.ico",
197
"content_html": post["content"],
198
"date_published": post["atom-post-time"],
199
"date_modified": post["atom-update-time"],
200
"url": "https://steve0greatness.github.io/blog/" + post["pathname"]
201
})
202
with open(BUILD_DIRECTORY + "/blog/feed.json", "w") as JSONFeedFile:
203
DumpJSON(CreatedJSON, JSONFeedFile)
204
205
def RenderLists():
206
Lists = GetLists()
207
CreateDirectory(BUILD_DIRECTORY + "/list/")
208
ListIndex = "<ul>"
209
for List in Lists:
210
FileLocation = "/list/" + List["filename"].replace(".yml", ".html")
211
Title = List["title"]
212
print("%s -> %s" % ("lists/" + List["filename"], BUILD_DIRECTORY + FileLocation))
213
with open(BUILD_DIRECTORY + FileLocation, "w") as file:
214
file.write(RenderTemplate("list.html", Content=List["content"], Title=Title, Location=FileLocation))
215
ListIndex += "<li><a href=\"%s\">%s</a></li>" % (FileLocation, Title)
216
ListIndex += "</ul>"
217
print("Building list index")
218
with open(BUILD_DIRECTORY + "/list/index.html", "w") as file:
219
file.write(RenderTemplate("list-index.html", Content=ListIndex))
220
221
def main():
222
global PostList
223
PostList = GetBlogList()
224
print("Wiping directory")
225
WipeFinalDir()
226
print("Creating blog holder")
227
CreateDirectory(BUILD_DIRECTORY + "/blog")
228
print("Rendering posts")
229
RenderPosts()
230
CreateJSONFeed()
231
print("Copying static directory")
232
CopyDirectory("static", BUILD_DIRECTORY)
233
print("Creating lists")
234
RenderLists()
235
236
print("Building pages")
237
for file, path in PAGES.items():
238
AllowSitemap = file not in DISALLOWED_SITEMAP
239
RenderPage(file, path, AllowSitemap, PostList=PostList)
240
241
print("Building redirects")
242
for OldLocation, NewLocation in REDIRECTS.items():
243
RenderPage("redirect.html", OldLocation, False, redirect=NewLocation, old=OldLocation)
244
245
with open(BUILD_DIRECTORY + "/sitemap.txt", "w") as SitemapFile:
246
SitemapFile.write("\n".join(sitemap))
247
248
if __name__ == "__main__":
249
main()