---
title: "透過 GitHub Actions 更新筆記內容 | Update note with GitHub Actions"
description: 透過 GitHub Actions 更新筆記內容.
image: https://user-images.githubusercontent.com/26391143/156984539-606601e9-ad2c-48d6-a783-f6a95bf0bd44.png
author: Hsins
tags: HackMD-Theme, HackMD-API
---
{%hackmd @themes/notion %}
<div style="text-align:center;">

# 透過 GitHub Actions 更新筆記內容
</div>
> **使用範例**:透過 GitHub Actions 更新筆記內容
> **提案人員**:[@Hsins (H.-H. Peng)](https://hackmd.io/@Hsins)
> **聯絡方式**:[hsinspeng@gmail.com](hsinspeng@gmail.com)
> **專案倉庫**:[Hsins/hackmd-themes](https://github.com/Hsins/hackmd-themes)
<details>
<summary>目錄(🔎 點擊展開)</summary>
[toc]
</details>
## 範例說明
### 自訂主題
[HackMD](https://hackmd.io/) 允許使用者在文件中添加如下的 [**內部樣式表**](https://developer.mozilla.org/en-US/docs/Web/HTML/Element/style) 來變更文件樣式:
``` html
<style>
p {
color: #26b72b;
}
</style>
```
並且可以透過如下的語法在其他文件中嵌入既有文件:
- **固定連結**:`{%hackmd @Hsins/theme-notion %}`
- **筆記代號**:`{%hackmd apDKTl3FRzG2MMi8U2L4Mw %}`
因此使用者可以透過在一份文件中定義好樣式主題後,在其他文件中透過文件標識碼 `noteId` 或自訂的永久連結來套用樣式主題。
### 壓縮體積
在 Yahoo! 開發者團隊多年前的文章 [Best Practices for Speeding Up Your Web Site](https://developer.yahoo.com/performance/rules.html) 中曾提到:
==_Minification is the practice of removing unnecessary characters from code to reduce its size thereby improving load times._==
由於 HackMD 添加樣式的方式是透過嵌入他篇文章的 CSS 樣式來達成效果,我們可以利用一系列的工具來完成縮小 CSS 樣式大小的操作:
- 開發者在 `*.css` 文件中實作並調整樣式,此檔案須交由版本控制軟體進行追蹤
- 提交代碼後,透過 GitHub Actions 觸發任務
1. 透過 CSS 後處理器(Postprocessors) [PostCSS](https://github.com/postcss/postcss) 處理瀏覽器兼容問題並最小化體積
2. 將最小化後的 CSS 樣式填入 `*.md` 文件中
3. 同步更新對應 `noteId` 的文件
## 實作說明
### 目錄架構
以專案 [hackmd-themes](https://github.com/Hsins/hackmd-themes) 為例,其目錄架構如下所示:
```
.
├── .github
│ └── workflows
│ ├── update-themes.yaml
│ └── ...
├── commands
│ ├── update.js
│ └── utils.js
├── styles
│ └── [theme-slug].css
├── themes
│ └── [theme-slug].md
├── configs.js
├── package.json
├── postcss.config.cjs
└── ...
```
- `./.github/workflows/update-themes.yaml` 定義了 GitHub Actions 工作流的觸發事件與具體行為
- `./commands` 存放相關的腳本程式
- `./styles` 存放 `[theme-slug].css` 檔案,主要開發更動都在此處
- `./themes` 存放 `[theme-slug].md` 檔案,會根據設定檔案由 GitHub Actions 執行腳本生成
- `./configs.js` 中存放設定檔案
### 內容設定
設定檔案 `./configs.js` 中存放了 API 設定、路徑設定與主題資訊,其中主題資訊定義結構如下:
``` javascript
// configs.js
export const themes = [
{
slug: 'theme-notion',
noteId: 'apDKTl3FRzG2MMi8U2L4Mw',
styleFile: 'notion.css',
themeFile: 'notion.md',
metadata: {
name: 'HackMD Theme - Notion',
description:
'Use `{%hackmd @Hsins/theme-notion %}` syntax to include this theme.',
tags: ['HackMD-Theme'],
},
}
// ...
];
```
其中 `noteId` 為筆記代號,可以透過 [User Notes API](https://hackmd.io/@hackmd-api/user-notes-api) 獲取,或是從筆記頁面的網址後綴取得。
> 此處也可以添加一個命令 `yarn create`,透過 HackMD API 創建筆記後,將返回的文章編號填入設定檔中,以供後續開發使用。
### 核心程式
由於作為樣式主題的 HackMD 檔案所需要的內容,只會由兩部分組成:
- YAML Matadata 部分
- CSS Stylesheet 部分
主要程式如下:
``` javascript
// update.js
import { getMetadata, getStyle, updateTheme, uploadTheme } from './utils.js';
import { themes } from '../configs.js';
themes.forEach((theme) => {
const metadata = getMetadata(theme);
const style = getStyle(theme);
const content = metadata + '\n' + style;
updateTheme(theme, content);
uploadTheme(theme, content);
});
```
其中 `uploadTheme()` 使用 [`axios`](https://github.com/axios/axios) 函數庫與 HackMD API 交互,透過指定的 `noteId` 更新內容:
``` javascript
// utils.js
import log from 'log-beautify';
import axios from 'axios';
import { HACKMD_API_URL, HACKMD_API_TOKEN } from '../configs.js';
const uploadTheme = (theme, content) => {
const axiosConfig = {
method: 'patch',
url: `${HACKMD_API_URL}/notes/${theme.noteId}`,
headers: {
'Authorization': HACKMD_API_TOKEN,
'Content-Type': 'application/json',
},
data: JSON.stringify({ content }),
};
axios(axiosConfig)
.then((response) => log.success(`Theme upload: ${theme.slug}.`))
.catch((error) => log.error(error));
};
```
### 環境變數
由於 API Token 屬於私密訊息,應妥善保存且不以明碼方式存放於程式中,此處可以針對專案倉庫創建一個 [環境(Environment)](https://docs.github.com/en/actions/deployment/targeting-different-environments/using-environments-for-deployment) 並將 Token 存放於其 [加密機密(Encrypted secrets)](https://docs.github.com/en/actions/security-guides/encrypted-secrets) 中:
<div style="text-align:center;">

</div>
在 [`update-themes.yaml`](https://github.com/Hsins/hackmd-themes/blob/main/.github/workflows/update-themes.yaml) 設定中,需要指定環境以及使用的環境變數:
``` yaml=8
jobs:
update-themes:
# 指定環境
environment: CI
runs-on: ubuntu-latest
```
``` yaml=27
- name: Update themes and upload to HackMD
run: yarn update
env:
# 設定環境變數
HACKMD_API_TOKEN: ${{ secrets.HACKMD_API_TOKEN }}
```
## 後記
希望可以在目前的 HackMD API 基礎上,添加以下功能:
- 更新筆記固定連結
- 使用範本創建筆記
## 參考資料
- [HackMD API Documentation](https://hackmd.io/@hackmd-api/developer-portal)
- [GitHub Actions Documentation](https://docs.github.com/en/actions)
- [Best Practices for Speeding Up Your Web Site | Yahoo! Developer](https://developer.yahoo.com/performance/rules.html)
- [在筆記中嵌入另一篇筆記 | HackMD 使用教學](https://hackmd.io/c/tutorials-tw/%2Fs%2Fhow-to-embed-note-tw)
- [嵌入另一篇筆記,自訂背景主題 | HackMD 使用教學](https://hackmd.io/c/tutorials-tw/%2Fs%2FoaYqEJsHR3m4IwBqEeu2Mg)
- [用固定網址發布筆記 | HackMD 使用教學](https://hackmd.io/c/tutorials-tw/%2Fs%2Fhow-to-share-note-tw)
<!-- Widgets: License -->
{%hackmd @Hsins/widget-license %}
<!-- Widgets: Likecoin -->
{%hackmd @Hsins/widget-likecoin %}