Markdown to Textile Converter for Redmine
English | 繁體中文

English
Overview
A Visual Studio Code extension that converts Markdown syntax to Textile markup format specifically optimized for Redmine. This tool is designed for users who need to migrate content from Markdown-based systems to Redmine's Textile markup format, supporting all common Redmine Textile features including tables and code blocks with syntax highlighting.
Features
- In-Place Conversion: Select Markdown text in the editor and convert it directly to Textile format
- Rich Syntax Support: Supports common Markdown elements including:
- Headings (h1-h6)
- Bold and italic text
- Links and images
- Ordered and unordered lists
- Code blocks with syntax highlighting (Redmine CodeRay format)
- Inline code
- Tables with alignment support
- Blockquotes
- Horizontal rules
- Line breaks
- Mermaid diagrams (Redmine plugin format)
- AST-Based Parser: Uses Abstract Syntax Tree for accurate conversion
- Context Menu Integration: Right-click on selected text to convert
- User-Friendly: Shows success/error notifications for all operations
Installation
From Source
Clone this repository:
git clone https://github.com/yourusername/vscode-markdown-to-textile.git
cd vscode-markdown-to-textile
Install dependencies:
pnpm install
Compile the extension:
pnpm run compile
Press F5 in VS Code to open a new Extension Development Host window
Usage
- Open a file with Markdown content in VS Code
- Select the Markdown text you want to convert
- Right-click and choose "Convert Markdown to Textile" from the context menu
- Or open Command Palette (Ctrl+Shift+P / Cmd+Shift+P) and run "Convert Markdown to Textile"
- The selected text will be replaced with Textile markup
Syntax Conversion Examples
| Markdown |
Textile (Redmine) |
# Heading 1 |
h1. Heading 1 |
## Heading 2 |
h2. Heading 2 |
**bold** |
*bold* |
*italic* |
_italic_ |
[link](https://github.com/mike-zheng/vscode-markdown-to-textile/blob/HEAD/url) |
"link":url |
 |
!image.jpg(alt)! |
`code` |
%{font-size: 0.85em;padding: 0.2em 0.4em;background-color: #656c7633;border-radius: 3px;font-weight:bold;}code% |
`code` (in table) |
@code@ |
`` `code` `` |
Displays literal `code` with backticks |
`%PATH%` |
%{...}%PATH%% (% escaped) |
`` `%PATH%` `` |
Displays literal `%PATH%` with backticks |
- item |
* item |
1. item |
# item |
> quote |
bq. quote |
Smart Spacing:
The converter automatically adds spaces inside Textile formatting markers when adjacent to text without spaces:
AB**C**. → AB* C*. (space added before C)
test**bold**text → test* bold *text (spaces added on both sides)
AB **C** . → AB *C* . (existing spaces preserved)
This ensures proper Textile rendering, as markers like *bold* and _italic_ require word boundaries.
Nested Lists
| Markdown |
Textile (Redmine) |
- Item 1 - Nested 1 - Nested 2 - Item 2 |
* Item 1 ** Nested 1 ** Nested 2 * Item 2 |
1. First 1. Nested first 2. Nested second 2. Second |
# First ## Nested first ## Nested second # Second |
- Level 1 - Level 2 - Level 3 |
* Level 1 ** Level 2 *** Level 3 |
Note: Nested lists are created by indenting with 2 or more spaces. The number of * or # markers indicates the nesting level in Textile format.
| Markdown |
Textile (Redmine) |
```javascript code here ``` |
<pre><code class="javascript"> code here </code></pre> |
```python code here ``` |
<pre><code class="python"> code here </code></pre> |
``` code here ``` |
<pre><code> code here </code></pre> |
| Markdown |
Textile (Redmine) |
```mermaid graph TD A[Start] --> B[End]; ``` |
{{mermaid graph TD A["Start"] --> B["End"]; }} |
Note: Mermaid diagrams are converted to Redmine's {{mermaid}} plugin format. Node labels in square brackets [text] are automatically converted to double-quoted format ["text"] for better compatibility. Requires the Redmine Mermaid macro plugin to be installed.
| Markdown |
Textile (Redmine) |
| Header 1 | Header 2 | |----------|----------| | Cell 1 | Cell 2 | |
|_. Header 1 |_. Header 2 | |Cell 1|Cell 2| |
| Left | Center | Right | |:-----|:------:|------:| | L | C | R | |
|_. Left |_. Center |_. Right | |L|=. C|>. R| |
| Name | Code | |------|------| | Test | `code` | |
|_. Name |_. Code | |Test|@code@| |
Note: Tables support left, center (=.), and right (>.) alignment in Redmine Textile format. Inline code in tables uses @code@ format instead of the styled format used outside tables.
Development Process
Project Architecture
The extension consists of three main modules:
extension.ts - Main entry point
- Registers the conversion command
- Handles editor interactions
- Manages user feedback
markdown-ast.ts - Markdown Parser
- Tokenizes Markdown input
- Builds Abstract Syntax Tree (AST)
- Handles nested structures
textile-generator.ts - Textile Generator
- Traverses AST nodes
- Generates Textile syntax
- Formats output
Development Setup
Prerequisites
Node.js >= 22.x
pnpm >= 10.x
Visual Studio Code >= 1.109.0
Install Dependencies
pnpm install
Development Tasks
- Compile once:
pnpm run compile
- Watch mode:
pnpm run watch
- Run tests:
pnpm test
- Compile tests only:
pnpm run compile-tests
- Lint code:
pnpm run lint
Testing
The extension includes comprehensive unit tests covering all conversion features:
# Run all tests (compile, lint, and test)
pnpm test
Test Coverage:
- Basic text formatting (bold, italic)
- Headings (H1-H6)
- Links and images
- Inline code with special character escaping
- Code blocks with language support
- Lists (ordered and unordered)
- Tables with alignment
- Blockquotes
- Complex mixed content
- Edge cases and Chinese content
Test Files:
src/test/extension.test.ts - Unit tests for parser and generator
test-conversion.md - Comprehensive manual test examples
test-inline-code.md - Inline code special cases
Note: Test runner will download VS Code test instance on first run. Make sure no other VS Code instances conflict with the test environment.
Build for Production
# Compile with production optimization
pnpm run package
Package as VSIX
Create a .vsix package for distribution or local installation:
# Install packaging tool (one-time setup)
pnpm add -D @vscode/vsce
# Package the extension
npx @vscode/vsce package
This generates markdown-to-textile-0.0.1.vsix in the project root.
Install the packaged extension:
Project Structure
vscode-markdown-to-textile/
├── src/
│ ├── extension.ts # Extension entry point
│ ├── markdown-ast.ts # Markdown parser
│ ├── textile-generator.ts # Textile generator
│ └── test/
│ └── extension.test.ts # Unit tests
├── dist/ # Compiled output
├── .vscode/
│ └── tasks.json # Build tasks
├── package.json # Extension manifest
├── tsconfig.json # TypeScript config
└── webpack.config.js # Webpack config
Technical Stack
- Language: TypeScript 5.9+
- Framework: VS Code Extension API
- Build Tool: Webpack 5
- Testing: Mocha + VS Code Test Framework
- Linting: ESLint with TypeScript ESLint
Key Implementation Details
- Parser Design: The Markdown parser uses a character-by-character scanning approach to tokenize input and construct an AST
- AST Structure: Each node contains type information and optional attributes (level, url, language, etc.)
- Generator Pattern: The Textile generator recursively traverses the AST and generates corresponding Textile syntax
- Error Handling: Comprehensive try-catch blocks with user-friendly error messages
Requirements
- Visual Studio Code version 1.109.0 or higher
- No external dependencies required at runtime
Known Issues
- Complex nested structures may require manual adjustment
- Some advanced Markdown features (footnotes, task lists) are not yet supported
- HTML embedded in Markdown is not converted
- Nested tables are not supported
Contributing
Contributions are welcome! Please feel free to submit a Pull Request.
License
MIT License
繁體中文
概述
這是一個專為 Redmine 優化的 Visual Studio Code 擴充功能,能將 Markdown 語法轉換為 Textile 標記格式。此工具專為需要將內容遷移到 Redmine 的 Textile 標記格式的使用者設計,支援所有常見的 Redmine Textile 功能,包括表格和帶有語法高亮的程式碼區塊。
功能特色
- 就地轉換:在編輯器中選取 Markdown 文字並直接轉換為 Textile 格式
- 豐富的語法支援:支援常見的 Markdown 元素,包括:
- 標題(h1-h6)
- 粗體和斜體文字
- 連結和圖片
- 有序和無序列表
- 帶有語法高亮的程式碼區塊(Redmine CodeRay 格式)
- 行內程式碼
- 支援對齊的表格
- 引用區塊
- 水平分隔線
- 換行符號
- Mermaid 圖表(Redmine 插件格式)
- 基於 AST 的解析器:使用抽象語法樹確保精確轉換
- 右鍵選單整合:右鍵點擊選取的文字即可轉換
- 使用者友善:所有操作都會顯示成功/錯誤通知
安裝方式
從原始碼安裝
複製此儲存庫:
git clone https://github.com/yourusername/vscode-markdown-to-textile.git
cd vscode-markdown-to-textile
安裝相依套件:
pnpm install
編譯擴充功能:
pnpm run compile
在 VS Code 中按 F5 開啟新的擴充功能開發視窗
使用方法
- 在 VS Code 中開啟包含 Markdown 內容的檔案
- 選取要轉換的 Markdown 文字
- 右鍵點擊並從選單中選擇 「Convert Markdown to Textile」
- 或開啟命令面板(Ctrl+Shift+P / Cmd+Shift+P)並執行 「Convert Markdown to Textile」
- 選取的文字將被替換為 Textile 標記
語法轉換範例
基本格式
| Markdown |
Textile (Redmine) |
# 標題 1 |
h1. 標題 1 |
## 標題 2 |
h2. 標題 2 |
**粗體** |
*粗體* |
*斜體* |
_斜體_ |
[連結](https://github.com/mike-zheng/vscode-markdown-to-textile/blob/HEAD/url) |
"連結":url |
 |
!image.jpg(替代文字)! |
`程式碼` |
%{font-size: 0.85em;padding: 0.2em 0.4em;background-color: #656c7633;border-radius: 3px;font-weight:bold.}程式碼% |
`程式碼` (在表格中) |
@程式碼@ |
`` `程式碼` `` |
顯示字面的 `程式碼` 包含反引號 |
`%PATH%` |
%{...}%PATH%% (百分號轉義) |
`` `%PATH%` `` |
顯示字面的 `%PATH%` 包含反引號 |
- 項目 |
* 項目 |
1. 項目 |
# 項目 |
> 引用 |
bq. 引用 |
智能空格處理:
轉換器會在 Textile 格式標記內側自動添加空格(當相鄰文字無空格時):
AB**C**. → AB* C*.(在 C 前添加空格)
test**bold**text → test* bold *text(兩側都添加空格)
AB **C** . → AB *C* .(保持現有空格)
這確保了正確的 Textile 渲染,因為 *粗體* 和 _斜體_ 這類標記需要字詞邊界。
嵌套列表
| Markdown |
Textile (Redmine) |
- 項目 1 - 嵌套 1 - 嵌套 2 - 項目 2 |
* 項目 1 ** 嵌套 1 ** 嵌套 2 * 項目 2 |
1. 第一 1. 嵌套第一 2. 嵌套第二 2. 第二 |
# 第一 ## 嵌套第一 ## 嵌套第二 # 第二 |
- 層級 1 - 層級 2 - 層級 3 |
* 層級 1 ** 層級 2 *** 層級 3 |
注意:嵌套列表通過縮進 2 個或更多空格來創建。* 或 # 標記的數量表示 Textile 格式中的嵌套層級。
程式碼區塊(Redmine 格式)
| Markdown |
Textile (Redmine) |
```javascript 程式碼內容 ``` |
<pre><code class="javascript"> 程式碼內容 </code></pre> |
```python 程式碼內容 ``` |
<pre><code class="python"> 程式碼內容 </code></pre> |
``` 程式碼內容 ``` |
<pre><code> 程式碼內容 </code></pre> |
Mermaid 圖表(Redmine 插件格式)
| Markdown |
Textile (Redmine) |
```mermaid graph TD A[開始] --> B[結束]; ``` |
{{mermaid graph TD A["開始"] --> B["結束"]; }} |
注意:Mermaid 圖表會轉換為 Redmine 的 {{mermaid}} 插件格式。方括號中的節點標籤 [文字] 會自動轉換為雙引號格式 ["文字"] 以獲得更好的相容性。需要安裝 Redmine Mermaid macro 插件。
表格(Redmine 格式)
| Markdown |
Textile (Redmine) |
| 標題 1 | 標題 2 | |--------|--------| | 內容 1 | 內容 2 | |
|_. 標題 1 |_. 標題 2 | |內容 1|內容 2| |
| 左對齊 | 置中 | 右對齊 | |:------|:----:|------:| | L | C | R | |
|_. 左對齊 |_. 置中 |_. 右對齊 | |L|=. C|>. R| |
| 名稱 | 程式碼 | |------|--------| | 測試 | `code` | |
|_. 名稱 |_. 程式碼 | |測試|@code@| |
注意:表格支援在 Redmine Textile 格式中的左對齊、置中(=.)和右對齊(>.)。表格中的行內程式碼使用 @code@ 格式,而非表格外使用的樣式格式。
開發流程
專案架構
此擴充功能由三個主要模組組成:
extension.ts - 主要入口點
markdown-ast.ts - Markdown 解析器
- 將 Markdown 輸入進行分詞
- 建立抽象語法樹(AST)
- 處理巢狀結構
textile-generator.ts - Textile 生成器
- 遍歷 AST 節點
- 生成 Textile 語法
- 格式化輸出
開發環境設定
先決條件
Node.js >= 22.x
pnpm >= 10.x
Visual Studio Code >= 1.109.0
安裝相依套件
pnpm install
開發任務
- 單次編譯:
pnpm run compile
- 監視模式:
pnpm run watch
- 執行測試:
pnpm test
- 僅編譯測試:
pnpm run compile-tests
- 程式碼檢查:
pnpm run lint
測試機制
擴充功能包含完整的單元測試,涵蓋所有轉換功能:
# 執行所有測試(編譯、檢查、測試)
pnpm test
測試涵蓋範圍:
- 基本文字格式(粗體、斜體)
- 標題(H1-H6)
- 連結和圖片
- 內聯程式碼與特殊字元轉義
- 程式碼區塊與語言支援
- 清單(有序和無序)
- 表格與對齊
- 引用區塊
- 複雜混合內容
- 邊界案例和中文內容
測試檔案:
src/test/extension.test.ts - 解析器和生成器的單元測試
test-conversion.md - 完整的手動測試範例
test-inline-code.md - 內聯程式碼特殊案例
注意:測試執行器會在首次執行時下載 VS Code 測試環境。請確保沒有其他 VS Code 實例與測試環境衝突。
建置正式版本
# 以正式版本模式編譯並優化
pnpm run package
打包成 VSIX
建立 .vsix 套件用於分發或本機安裝:
# 安裝打包工具(僅需執行一次)
pnpm add -D @vscode/vsce
# 打包擴充功能
npx @vscode/vsce package
這會在專案根目錄生成 markdown-to-textile-0.0.1.vsix 檔案。
安裝已打包的擴充功能:
專案結構
vscode-markdown-to-textile/
├── src/
│ ├── extension.ts # 擴充功能入口點
│ ├── markdown-ast.ts # Markdown 解析器
│ ├── textile-generator.ts # Textile 生成器
│ └── test/
│ └── extension.test.ts # 單元測試
├── dist/ # 編譯輸出
├── .vscode/
│ └── tasks.json # 建置任務
├── package.json # 擴充功能清單
├── tsconfig.json # TypeScript 設定
└── webpack.config.js # Webpack 設定
技術堆疊
- 程式語言:TypeScript 5.9+
- 框架:VS Code Extension API
- 建置工具:Webpack 5
- 測試:Mocha + VS Code Test Framework
- 程式碼檢查:ESLint with TypeScript ESLint
關鍵實作細節
- 解析器設計:Markdown 解析器採用逐字元掃描方式進行分詞並建構 AST
- AST 結構:每個節點包含類型資訊和可選屬性(層級、網址、語言等)
- 生成器模式:Textile 生成器遞迴遍歷 AST 並生成對應的 Textile 語法
- 錯誤處理:完整的 try-catch 區塊配合使用者友善的錯誤訊息
系統需求
- Visual Studio Code 版本 1.109.0 或更高
- 執行時不需要外部相依套件
已知問題
- 複雜的巢狀結構可能需要手動調整
- 部分進階 Markdown 功能(註腳、任務清單)尚未支援
- Markdown 中嵌入的 HTML 不會被轉換
- 不支援巢狀表格
貢獻
歡迎貢獻!請隨時提交 Pull Request。
授權
MIT License
Enjoy!