概要
一目瞭然、私のGatsbyによるヘッドレスWordPressブログはCSSがなっていません。
とりあえずソースコードだけでも色付けしたいと思いました。
これを次のようにしました。
使用したパッケージ
sugar-highを用いました。まだ新しいのパッケージなので使用は注意が必要と思います。
$ yarn add sugar-hig
sugar-highを用いた関数
src\util\highlightCode.js というコードを追加しました。highlightCodeContents という関数をエクスポートしています。
import { highlight } from 'sugar-high';
const entityConvert = (org_string) => {
let converted = org_string.replace(/(<)/g,"<");
converted = converted.replace(/(>)/g,">");
return (converted);
}
const removeCodeTags = (org_string) => {
let converted = org_string.replace("<code xmlns=\"http://www.w3.org/1999/xhtml\">","");
converted = converted.replace("</code>","");
return (converted);
}
export function highlightCodeContents(htmlContent) {
try {
// HTML文字列をDOMのDocumentとして解釈
const parser = new DOMParser();
const doc = parser.parseFromString(htmlContent, 'text/html');
if (doc === null) return htmlContent;
// コードブロック(<code> ... </code>)群を検索
const codes = doc.querySelectorAll('code');
// DOM ツリーを表すXML 文字列を構築するための準備
const serializer = new XMLSerializer();
// 各コードブロックを処理
codes.forEach((code) => {
let codeString = serializer.serializeToString(code); // codeタグの間を取りたいが、codeタグやエンティティ文字を含んでいたりいなかったり
codeString = entityConvert(codeString); // エンティティ文字を通常の文字へ変換
codeString = removeCodeTags(codeString);
codeString = highlight(codeString);
const newCode = document.createElement('code');
newCode.innerHTML = codeString
const parent = code.parentNode
parent.replaceChild(newCode, code);
});
// DOMツリーを表す文字列を構築
return serializer.serializeToString(doc);
} catch (ex) {
console.error(ex.message);
}
return htmlContent;
}
ブログ投稿の静的ファイルを作るコードの変更
src\templates\blog-post.js というコードを次のように2行変更しました。
:
import { highlightCodeContents } from '../util/highlightCode'; // 色付け関数をインポート
:
:
const BlogPostTemplate = ({ data: { previous, next, post } }) => {
:
{!!post.content && (
<ContentWrapper itemProp="articleBody">
{parse(highlightCodeContents(post.content))} // 色付け関数を使用
</ContentWrapper>
)}
sugar-high用及び<code>用のCSSの設定
src\style.css に次を追加しました。
.wp-block-code > code {
background-color: #193549;
}
.sh__class {
color: #66f2ff;
}
.sh__identifier {
color: #fff2d0;
}
.sh__sign {
color: #e1efff;
}
.sh__string {
color: #a5ff7e;
}
.sh__keyword {
color: #ff902f;
}
.sh__comment {
color: #0088ff;
}
その他
- gatsby developでテストする場合はその前に gatsby clean を実行します。
- 今回使用した関数だけを試すプロジェクトはこちらをご覧ください。
- ビルド時には次のようなエラーが出ました。Gatsby Cloudでも同様のエラーが出ています。しかし、コードは色付けされていました。
- これについては、次の1行を追加してエラーは出なくなりました。
export function highlightCodeContents(htmlContent) {
try {
if (typeof window === 'undefined') return htmlContent; <--- この1行
- Post TagsGatsby