-
Notifications
You must be signed in to change notification settings - Fork 0
/
Publish-GitPubJekyll.ps1
264 lines (257 loc) · 9.33 KB
/
Publish-GitPubJekyll.ps1
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
function Publish-GitPubJekyll {
<#
.SYNOPSIS
Publishes content as Jekyll Posts
.DESCRIPTION
Publishes content as Jekyll Posts.
.LINK
Get-GitPub
.LINK
Publish-GitPub
.EXAMPLE
Get-GitPubIssue -Repository GitPub -Owner StartAutomating |
Publish-GitPubJekyll
#>
[Reflection.AssemblyMetaData("GitPub.Publisher", $true)]
param(
# The title of the post.
[Parameter(Mandatory,ValueFromPipelineByPropertyName)]
[Alias('Title')]
[string]
$PostTitle,
# The body of the post.
[Parameter(Mandatory,ValueFromPipelineByPropertyName)]
[Alias('Body')]
[string]
$PostBody,
# The time the post was created.
[Parameter(Mandatory,ValueFromPipelineByPropertyName)]
[Alias('Created_At','CreationTime')]
[DateTime]
$PostCreationTime,
# The author of the post
[Parameter(ValueFromPipelineByPropertyName)]
[string]
$PostAuthor,
# One or more tags used for the post
[Parameter(ValueFromPipelineByPropertyName)]
[Alias('Tags')]
[string[]]
$PostTag,
# The layout used for a post.
[Parameter(ValueFromPipelineByPropertyName)]
[string]
$PostLayout,
# The source URL. If provided, this will be included in front matter.
[Parameter(ValueFromPipelineByPropertyName)]
[Alias('HTML_url')]
[string]
$SourceUrl,
# If not set, will summarize all posts in a given year, month, and day.
# This will generate a file for each unique year, year/month, day combination
# and will give them the appropriate permalinks.
[switch]
$NoSummary,
# If set, will not generate a feed.
[switch]
$NoFeed,
# The name of the RSS feed file to generate.
[string]
$FeedName = "rss.xml",
[string]
$FeedTemplate = @'
---
layout: null
---
<?xml version="1.0" encoding="UTF-8"?>
<rss version="2.0" xmlns:atom="http://www.w3.org/2005/Atom">
<channel>
<title>{{ site.title | xml_escape }}</title>
<description>{{ site.description | xml_escape }}</description>
<link>{{ site.url }}{{ site.baseurl }}/</link>
<atom:link href="{{ "/feed.xml" | prepend: site.baseurl | prepend: site.url }}" rel="self" type="application/rss+xml"/>
<pubDate>{{ site.time | date_to_rfc822 }}</pubDate>
<lastBuildDate>{{ site.time | date_to_rfc822 }}</lastBuildDate>
<generator>Jekyll v{{ jekyll.version }}</generator>
{% for post in site.posts limit:1000 %}
{% if post.sitemap != false %}
<item>
<title>{{ post.title | xml_escape }}</title>
<description>{{ post.content | xml_escape }}</description>
<pubDate>{{ post.date | date_to_rfc822 }}</pubDate>
<link>{{ post.url | prepend: site.baseurl | prepend: site.url }}</link>
<guid isPermaLink="true">{{ post.url | prepend: site.baseurl | prepend: site.url }}</guid>
{% for tag in post.tags %}
<category>{{ tag | xml_escape }}</category>
{% endfor %}
{% for cat in post.categories %}
<category>{{ cat | xml_escape }}</category>
{% endfor %}
</item>
{% endif %}
{% endfor %}
</channel>
</rss>
'@,
# The content used for a yearly summary
[Alias('AnnualSummary')]
[string]
$YearlySummary = @'
---
permalink: /$Year/
---
{% assign currentYear = "$Year" %}
{% for post in site.posts %}
{% assign postYear = post.date | date: "%Y" %}
{% assign postYearMonth = post.date | date: "[%B](%m) %Y" %}
{% if postYear != currentYear %}
{% continue %}
{% endif %}
{% if hasDisplayedYear != postYear %}
## [{{postYear}}](.)
{% endif %}
{% assign hasDisplayedYear = postYear %}
{% if hasDisplayedYearMonth != postYearMonth %}
### {{postYearMonth}}
{% endif %}
{% assign hasDisplayedYearMonth = postYearMonth %}
* [ {{ post.title }} ]( {{ post.url }} )
{% endfor %}
'@,
[ValidateSet('md','html')]
[Alias('YearlySummaryFormat','AnnualSummaryFormat', 'AnnualSummaryExtension')]
[string]
$YearlySummaryExtension = 'md',
[Alias('MonthSummary')]
[string]
$MonthlySummary = @'
---
permalink: /$Year/$Month/
---
{% assign currentYearMonth = "$Year $Month" %}
{% for post in site.posts %}
{% assign postYear = post.date | date: "%Y" %}
{% assign postYearMonth = post.date | date: "%B [%Y](..)" %}
{% assign postYM = post.date | date: "%Y %m" %}
{% if postYM != currentYearMonth %}
{% continue %}
{% endif %}
{% if hasDisplayedYearMonth != postYearMonth %}
## {{postYearMonth}}
{% endif %}
{% assign hasDisplayedYearMonth = postYearMonth %}
* [ {{ post.title }} ]( {{ post.url }} )
{% endfor %}
'@,
[Alias('MonthlySummaryFormat', 'MonthSummaryFormat','MonthSummaryExtension')]
[string]
$MonthlySummaryExtension = 'md',
[string]
$DailySummary = @'
---
permalink: /$Year/$Month/$Day/
---
{% for post in site.posts %}
{% assign currentdate = post.date | date: "%Y %m %d" %}
{% assign friendlydate = post.date | date: "[%B](..) [%d](.) [%Y](../..)" %}
{% if currentdate != "$Year $Month $Day" %}
{% continue %}
{% endif %}
{% if currentdate != date %}
## {{friendlydate}}
{% assign date = currentdate %}
{% endif %}
* [ {{ post.title }} ]( {{ post.url }} )
{% endfor %}
'@,
[Alias('DailySummaryFormat', 'DaySummaryFormat', 'DaySummaryExtension')]
[string]
$DailySummaryExtension = 'md',
# The output path. If not provided, will output to _posts in the current directory.
[string]
$OutputPath
)
begin {
if (-not $OutputPath) {
$OutputPath = Join-Path $pwd "_posts"
}
if (-not (Test-Path $OutputPath)) {
$null = New-Item -ItemType Directory -Path $OutputPath -Force
}
$MarkdownYamlHeader = [regex]::new(@'
\A\-{3,} # At least 3 dashes mark the start of the YAML header
(?<YAML>(?:.|\s){0,}?(?=\z|\-{3,} # And anything until at least three dashes is the content
))\-{3,} # Include the dashes in the match, so that the pointer is correct.
'@, 'Multiline,IgnorePatternWhitespace')
}
process {
$formattedDate = $PostCreationTime.ToLocalTime().ToString("yyyy-MM-dd")
$safeTitle = $PostTitle -replace '[\\/\<\>\:"\|\?\*]' -replace '\s', '-'
$postPath = Join-Path $OutputPath "$formattedDate-$safeTitle.md"
$yamlHeader = $MarkdownYamlHeader.Matches($Postbody)
$PostBody = $MarkdownYamlHeader.Replace($Postbody,'')
$frontMatter = [Ordered]@{PSTypeName='YamlHeader';title= $PostTitle -replace '-', ' '}
if ($PostLayout) {
$frontMatter['layout'] = $PostLayout
}
if ($PostAuthor) {
$frontMatter['author'] = $PostAuthor
}
if ($SourceUrl) {
$frontMatter['sourceURL'] = $SourceUrl
}
if ($PostTag) {
if ($PostTag.Length -eq 1) {
$frontMatter['tag'] = $PostTag[0]
} else {
$frontMatter['tags'] = $PostTag
}
}
$PostBody = @(
([PSCustomObject]$frontMatter | Out-String -Width 1kb).Trim()
$PostBody) -join [Environment]::NewLine
$PostBody | Set-Content -LiteralPath $postPath -Encoding utf8
Get-Item -LiteralPath $postPath
}
end {
$foundPosts = Get-ChildItem -Path $OutputPath -Filter "*.md"
$outputParentPath = Split-Path $OutputPath
if ((-not $NoFeed) -and $FeedName) {
$feedPath = (Join-Path $outputParentPath $FeedName)
$FeedTemplate | Set-Content -Path $feedPath -Encoding utf8
Get-Item $feedPath
}
if ($NoSummary) { return }
$summaryFiles = @{}
foreach ($postFound in $foundPosts) {
$postFoundDate = (@($postFound.Name -split '-',4)[0..2] -join '-') -as [DateTime]
if (-not $postFoundDate) {
continue
}
$year = $postFoundDate.ToString("yyyy")
$month = $postFoundDate.ToString("MM")
$day = $postFoundDate.ToString("dd")
foreach ($summaryName in 'Yearly','Monthly','Daily') {
$summaryContent = $ExecutionContext.SessionState.PSVariable.Get("${summaryName}Summary").Value
$summaryExtension = $ExecutionContext.SessionState.PSVariable.Get("${summaryName}SummaryExtension").Value.ToLower()
$summaryFilePath =
switch ($summaryName) {
Yearly {
Join-Path $outputParentPath "$year.$SummaryExtension"
}
Monthly {
Join-Path $outputParentPath "$year-$month.$SummaryExtension"
}
Daily {
Join-Path $outputParentPath "$year-$month-$day.$SummaryExtension"
}
}
if ($summaryFiles["$summaryFilePath"]) { continue }
$ExecutionContext.SessionState.InvokeCommand.ExpandString($summaryContent) |
Set-Content $summaryFilePath -Encoding UTF8
$summaryFiles["$summaryFilePath"] = Get-Item $summaryFilePath
$summaryFiles["$summaryFilePath"]
}
}
}
}