M _config.yml => _config.yml +7 -1
@@ 33,7 33,7 @@ masthead_title: # overrides the website title displayed in the masthead, use " "
# breadcrumbs: false # true, false (default)
words_per_minute: 200
comments:
- provider: "disqus" # false (default), "disqus", "discourse", "facebook", "google-plus", "staticman", "staticman_v2" "custom"
+ provider: "matrix" # false (default), "disqus", "discourse", "facebook", "google-plus", "staticman", "staticman_v2" "custom"
disqus:
shortname: "parto-blog" # https://help.disqus.com/customer/portal/articles/466208-what-s-a-shortname-
discourse:
@@ 49,6 49,12 @@ comments:
staticman:
branch: # "master"
endpoint: # "https://{your Staticman v3 API}/v3/entry/github/"
+ matrix:
+ homeserver_url: "https://eglo.ga"
+ homeserver: "eglo.ga"
+ site: "xdavidwu.eglo.ga"
+ admin: "@xdavidwu:eglo.ga"
+ bot: "@xdavidwu.eglo.ga-comment-bot:eglo.ga"
reCaptcha:
siteKey:
secret:
A => +10 -0
@@ 0,0 1,10 @@
<script>
initComments({
node: document.getElementById('comment-section'),
defaultHomeserverUrl: 'https://matrix-client.matrix.org',
serverName: '{{ site.comments.matrix.homeserver }}',
siteName: '{{ site.comments.matrix.site }}',
commentSectionId: '{{ page.url }}',
guestPostingEnabled: false,
})
</script>
M => +2 -0
@@ 12,6 12,8 @@
{% include /comments-providers/staticman_v2.html %}
{% when "utterances" %}
{% include /comments-providers/utterances.html %}
{% when "matrix" %}
{% include /comments-providers/matrix.html %}
{% when "custom" %}
{% include /comments-providers/custom_scripts.html %}
{% endcase %}
M => +3 -0
@@ 155,6 155,9 @@
{% when "utterances" %}
<h4 class="page__comments-title">{{ comments_label }}</h4>
<section id="utterances-comments"></section>
{% when "matrix" %}
<h4 class="page__comments-title">Comments on Matrix #comments_{{ site.comments.matrix.site }}_{{ page.url }}:{{ site.comments.matrix.homeserver }}</h4>
<div id="comment-section"></div>
{% when "custom" %}
{% include /comments-providers/custom.html %}
{% endcase %}
M _includes/head.html => _includes/head.html +4 -0
@@ 7,6 7,10 @@
<script>
document.documentElement.className = '';
</script>
+{% if site.comments.provider == "matrix" and page.comments %}
+ <script type="text/javascript" src="https://latest.cactus.chat/cactus.js"></script>
+ <link rel="stylesheet" href="https://latest.cactus.chat/style.css" type="text/css">
+{% endif %}
<link rel="stylesheet" href="{{ '/assets/css/main.css' | relative_url }}">
<link rel="stylesheet" href="https://cdn.jsdelivr.net/npm/fork-awesome@1.1.7/css/fork-awesome.min.css" integrity="sha256-gsmEoJAws/Kd3CjuOQzLie5Q3yshhvmo7YNtBG7aaEY=" crossorigin="anonymous">
<link rel="stylesheet" href="https://cdn.jsdelivr.net/npm/fork-awesome@1.1.7/css/v5-compat.min.css" integrity="sha384-1zW94WHdRLtWmM3xxKcAULg/IDeSsb7kofYSkI2jlXTRLO9UXrZcxB1Xi7jQ18Fg" crossorigin="anonymous">
A _plugins/matrix-room-provision.rb => _plugins/matrix-room-provision.rb +60 -0
@@ 0,0 1,60 @@
+require 'net/http'
+require 'json'
+
+Jekyll::Hooks.register :site, :after_init do |site|
+ $config = site.config
+end
+
+Jekyll::Hooks.register :posts, :post_write do |page|
+ if $config['comments']['provider'] != 'matrix'
+ return
+ end
+
+ Jekyll.logger.info 'Checking Matrix room for post:', page.data['title']
+ hs_url = $config['comments']['matrix']['homeserver_url']
+ hs = $config['comments']['matrix']['homeserver']
+ site = $config['comments']['matrix']['site']
+ room_alias_local = "comments_#{site}_#{page.url}"
+ room_alias = "##{room_alias_local}:#{hs}"
+
+ alias_encoded = ERB::Util.url_encode room_alias
+ alias_resolve_uri = URI hs_url + "/_matrix/client/r0/directory/room/#{alias_encoded}"
+ res = Net::HTTP.get_response alias_resolve_uri
+
+ if res.is_a? Net::HTTPNotFound
+ Jekyll.logger.info 'Creating Matrix room:', room_alias
+ create_room_uri = URI hs_url + '/_matrix/client/r0/createRoom'
+ req = Net::HTTP::Post.new create_room_uri, 'Content-Type' => 'application/json', 'Authorization' => "Bearer #{ENV['MATRIX_ACCESS_TOKEN']}"
+ req.body = {
+ visibility: 'private',
+ room_alias_name: room_alias_local,
+ name: "#{page.data['title']}",
+ topic: "Comments of \"#{page.data['title']}\" in #{site} at #{$config['url'] + page.url}",
+ invite: [$config['comments']['matrix']['admin']],
+ creation_content: {
+ 'm.federate': true,
+ },
+ preset: 'public_chat',
+ initial_state: [
+ {
+ type: 'm.room.history_visibility',
+ content: {
+ history_visibility: 'world_readable',
+ },
+ },
+ ],
+ power_level_content_override: {
+ users: {
+ $config['comments']['matrix']['admin'] => 100,
+ $config['comments']['matrix']['bot'] => 100,
+ },
+ },
+ }.to_json
+ res = Net::HTTP.start create_room_uri.hostname, create_room_uri.port, use_ssl: true do |http|
+ http.request req
+ end
+ Jekyll.logger.info "createRoom returns:", res.body
+ end
+
+ Jekyll.logger.info ""
+end
M _sass/minimal-mistakes/_buttons.scss => _sass/minimal-mistakes/_buttons.scss +1 -1
@@ 6,7 6,7 @@
Default button
========================================================================== */
-.btn {
+.btn, .cactus-button {
/* default */
display: inline-block;
margin-bottom: 0.25em;
M _sass/minimal-mistakes/_colors.scss => _sass/minimal-mistakes/_colors.scss +12 -0
@@ 597,3 597,15 @@ a.reversefootnote {
.required {
color: $danger-color;
}
+
+@if $comments-provider == matrix {
+ .cactus-login-form {
+ background-color: $background-color;
+ }
+ .cactus-login-field {
+ > input {
+ border-color: $border-color;
+ color: $text-color;
+ }
+ }
+}
M _sass/minimal-mistakes/_forms.scss => _sass/minimal-mistakes/_forms.scss +91 -60
@@ 2,18 2,18 @@
/* ==========================================================================
Forms
========================================================================== */
-
+
form {
margin: 0 0 5px 0;
padding: 1em;
background-color: $form-background-color;
-
+
fieldset {
margin-bottom: 5px;
padding: 0;
border-width: 0;
}
-
+
legend {
display: block;
width: 100%;
@@ 23,22 23,22 @@
border: 0;
white-space: normal;
}
-
+
p {
margin-bottom: (5px / 2);
}
-
+
ul {
list-style-type: none;
margin: 0 0 5px 0;
padding: 0;
}
-
+
br {
display: none;
}
}
-
+
label,
input,
button,
@@ 46,31 46,31 @@
textarea {
vertical-align: baseline;
}
-
+
input,
button,
select,
textarea {
box-sizing: border-box;
}
-
+
label {
display: block;
margin-bottom: 0.25em;
color: $text-color;
cursor: pointer;
-
+
small {
font-size: $type-size-6;
}
-
+
input,
textarea,
select {
display: block;
}
}
-
+
input,
textarea,
select {
@@ 84,15 84,15 @@
border-radius: $border-radius;
box-shadow: $box-shadow;
}
-
+
.input-mini {
width: 60px;
}
-
+
.input-small {
width: 90px;
}
-
+
input[type="image"],
input[type="checkbox"],
input[type="radio"] {
@@ 105,17 105,17 @@
border-radius: 0;
box-shadow: none;
}
-
+
input[type="checkbox"],
input[type="radio"] {
box-sizing: border-box;
padding: 0;
}
-
+
input[type="image"] {
border: 0;
}
-
+
input[type="file"] {
width: auto;
padding: initial;
@@ 125,7 125,7 @@
background-color: initial;
box-shadow: none;
}
-
+
input[type="button"],
input[type="reset"],
input[type="submit"] {
@@ 133,44 133,44 @@
height: auto;
cursor: pointer;
}
-
+
select {
width: auto;
background-color: #fff;
}
-
+
select[multiple],
select[size] {
height: auto;
}
-
+
textarea {
resize: vertical;
height: auto;
overflow: auto;
vertical-align: top;
}
-
+
input[type="hidden"] {
display: none;
}
-
+
.form {
position: relative;
}
-
+
.radio,
.checkbox {
padding-left: 18px;
font-weight: normal;
}
-
+
.radio input[type="radio"],
.checkbox input[type="checkbox"] {
float: left;
margin-left: -18px;
}
-
+
.radio.inline,
.checkbox.inline {
display: inline-block;
@@ 178,16 178,16 @@
margin-bottom: 0;
vertical-align: middle;
}
-
+
.radio.inline + .radio.inline,
.checkbox.inline + .checkbox.inline {
margin-left: 10px;
}
-
+
/*
Disabled state
========================================================================== */
-
+
input[disabled],
select[disabled],
textarea[disabled],
@@ 197,11 197,11 @@
opacity: 0.5;
cursor: not-allowed;
}
-
+
/*
Focus & active state
========================================================================== */
-
+
input:focus,
textarea:focus {
border-color: $primary-color;
@@ 209,60 209,60 @@
box-shadow: inset 0 1px 3px rgba($text-color, 0.06),
0 0 5px rgba($primary-color, 0.7);
}
-
+
input[type="file"]:focus,
input[type="radio"]:focus,
input[type="checkbox"]:focus,
select:focus {
box-shadow: none;
}
-
+
/*
Help text
========================================================================== */
-
+
.help-block,
.help-inline {
color: $muted-text-color;
}
-
+
.help-block {
display: block;
margin-bottom: 1em;
line-height: 1em;
}
-
+
.help-inline {
display: inline-block;
vertical-align: middle;
padding-left: 5px;
}
-
+
/*
.form-group
========================================================================== */
-
+
.form-group {
margin-bottom: 5px;
padding: 0;
border-width: 0;
}
-
+
/*
.form-inline
========================================================================== */
-
+
.form-inline input,
.form-inline textarea,
.form-inline select {
display: inline-block;
margin-bottom: 0;
}
-
+
.form-inline label {
display: inline-block;
}
-
+
.form-inline .radio,
.form-inline .checkbox,
.form-inline .radio {
@@ 270,36 270,36 @@
margin-bottom: 0;
vertical-align: middle;
}
-
+
.form-inline .radio input[type="radio"],
.form-inline .checkbox input[type="checkbox"] {
float: left;
margin-left: 0;
margin-right: 3px;
}
-
+
/*
.form-search
========================================================================== */
-
+
.form-search input,
.form-search textarea,
.form-search select {
display: inline-block;
margin-bottom: 0;
}
-
+
.form-search .search-query {
padding-left: 14px;
padding-right: 14px;
margin-bottom: 0;
border-radius: 14px;
}
-
+
.form-search label {
display: inline-block;
}
-
+
.form-search .radio,
.form-search .checkbox,
.form-inline .radio {
@@ 307,26 307,26 @@
margin-bottom: 0;
vertical-align: middle;
}
-
+
.form-search .radio input[type="radio"],
.form-search .checkbox input[type="checkbox"] {
float: left;
margin-left: 0;
margin-right: 3px;
}
-
+
/*
.form--loading
========================================================================== */
-
+
.form--loading:before {
content: "";
}
-
+
.form--loading .form__spinner {
display: block;
}
-
+
.form:before {
position: absolute;
top: 0;
@@ 336,7 336,7 @@
background-color: rgba(255, 255, 255, 0.7);
z-index: 10;
}
-
+
.form__spinner {
display: none;
position: absolute;
@@ 344,11 344,11 @@
left: 50%;
z-index: 11;
}
-
+
/*
Google search form
========================================================================== */
-
+
#goog-fixurl {
ul {
list-style: none;
@@ 359,7 359,7 @@
}
}
}
-
+
#goog-wm-qt {
width: auto;
margin-right: 10px;
@@ 374,9 374,40 @@
border-color: $border-color;
border-radius: $border-radius;
}
-
+
#goog-wm-sb {
@extend .btn;
}
-
+
+}
+@if $comments-provider == matrix {
+ .cactus-editor-textarea {
+ border-radius: $border-radius;
+ height: 120px;
+
+ &::placeholder {
+ line-height: 100px;
+ font-size: 1em;
+ }
+ }
+
+ // matrix.to fails with slash in localpart
+ .cactus-matrixdotto-button {
+ display: none !important;
+ }
+
+ .cactus-login-form {
+ box-shadow: 0 2px 4px 0 rgba(#000, 0.16), 0 2px 10px 0 rgba(#000, 0.12);
+ padding: 32px;
+ border-radius: $border-radius;
+ }
+
+ .cactus-login-field {
+ > input {
+ border: 0;
+ border-bottom: 1px solid;
+ background: transparent;
+ outline: none;
+ }
+ }
}