你覺得markdown只能用來寫文檔嗎?

Markdown

相信如今應該沒有人沒聽過markdown,若是你沒聽過,你該反思下,若是你沒用過,建議你從如今開始嘗試。markdown是一種基於文本的描述語言,什麼意思呢,通俗的講就是你只要靠鍵盤就能完成文章的排版,而且可讀性很高,Markdown由於其超級簡單的語法(十分鐘就能入門),可以擺脫萬惡的鼠標,友好的編輯界限,靈活的擴展性等特色迅速在開發人員間流行起來,成爲文檔編寫首選工具,github的README文檔默認使用markdown。html

markdown主要是用來寫文檔,在word的時代,寫文檔對於開發人員就是折磨,「文檔十分鐘,排版一小時」是很常見的,不只如此排出來每每仍是一坨狗屎,有了markdown以後,狀況就變了,你只需用md描述你的格式,具體排版就交給工具。前端

在寫文檔上,md描述的是文檔的格式,但做爲一門這麼優秀的描述語言,可不只僅能描述格式這麼簡單。java

Markdown繪製流程圖

咱們怎麼描述一個流程?用天然語言描述就是「A提交到B,B審批後流轉到C,C審批後流程結束」,用流程編排工具就是在界面上拖拽各類節點將每一個節點按照流程流轉規則鏈接,用程序描述就是後臺須要將流程信息結構化存儲,而且藉助流程引擎驅動流程。既然markdown是描述語言,能不能用markdown來描述流程,確定是能夠的,咱們拍腦殼想一個語法:mysql

A->B
B->C
C->END

這樣是否是描述好了,不用任何工具只需一個記事本咱們就描述好了一個流程,若是有程序可以基於這個規則驅動流程是否是就能夠用markdown描述流程了,你可能以爲實際流程還有不少信息markdown沒法描述,但僅考慮流程圖不考慮業務實現上,徹底是能夠用md描述清楚的,而且有人實現了,mermaid就是一個用md來繪製各類圖的項目,點擊這裏能夠體驗下用markdown繪製流程圖,繪製UML等,下面這個UML圖就是經過該工具進行繪製git

語法以下:github

sequenceDiagram
    participant AbapRepository
    participant BasicRepository
    participant JCoFunctionTemplate
    participant MetaDataStorage
    AbapRepository ->> BasicRepository : getFunction
    BasicRepository ->> MetaDataStorage :loadFunctionTemplate
    MetaDataStorage -->> BasicRepository :JCoFunctionTemplate
    BasicRepository ->> JCoFunctionTemplate :getFunction
    JCoFunctionTemplate -->> BasicRepository:new AbapFunction(this);
    BasicRepository --> AbapRepository:JCoFunction

介紹md繪製流程圖目的不是告訴有一個工具能夠用md繪製流程圖,並且想告訴你,md是描述語言,不是文檔語言,不是專門用來寫文檔的,任何須要描述的活動均可以用md實現,一旦你意識到了這個,事情就有趣了。sql

描述語言和模板語言

在jsp中,咱們能夠在html中插入java代碼,運行時會執行java代碼,最終完成完整的html渲染,這個就是一種模板語言。模板語言負責將數據和內容進行整合完成最終的渲染。java中較流行的模板語言有freemarker,velocity,jsp等,模板語言一個問題就是太偏技術,對非開發人員很不友好,對開發人員也不友好,寫起來很彆扭,若是md可以模板語言結合就完美,什麼意思呢,經過md提供數據,結合模板進行渲染。下面就經過一個具體的項目說明這個過程。數據庫

用Markdown建立表

在sql中,咱們能夠經過下面語句建立表:bash

-- Create table
create table MX_USER
(
    ID VARCHAR(100),
    NAME VARCHAR(100),
    EMAIL VARCHAR(100)
);

-- Add comments to the table
comment on table MX_USER
is '用戶表';

-- Add comments to the columns
comment on column MX_USER.ID
is '主鍵';
comment on column MX_USER.NAME
is '姓名';
comment on column MX_USER.EMAIL
is '郵箱';

-- Create primary, unique and foreign key constraints
alter table MX_USER
add constraint MX_USER_PK primary key (ID);

-- Create/Recreate indexes
create unique idx_name on (NAME,EMAIL);

以上sql完成了幾件事markdown

  • 建立表
  • 對錶進行備註
  • 對字段進行備註
  • 建立主鍵約束
  • 建立索引

若是要建立新的表就拷貝上面的sql稍加修改就行。

你會不會以爲這樣巨麻煩,反正我是以爲很麻煩,我想要的方式是這樣的

# mx_user

``text
用戶表
``

列名|類型|備註|默認值
---|---|---|---
*id|varchar(100)|主鍵|-
name|varchar(100)|姓名|-
email|varchar(100)|郵箱|-


### idx_name
- name
- email

我本身定了一些規則:

  • #表示建立新表
  • text備註表示對錶進行備註
  • 列信息放在表格裏,表格列分別爲,列名,類型,備註,默認值,除了列名和類型是必須,其餘都是可選。
  • 主鍵列列明前面加*號
  • 索引用###表示,索引列用-表示

方案以下:

  • 解析markdown,獲取結構化數據
  • 結合velocity模板生成最終的sql

commonmark-java是一個解析markdown的java庫,藉助commonmark能夠完成對markdown的解析,這裏不對具體解析過程進行講解,源碼已經上傳至github,能夠點擊這裏獲取源碼,解析後獲取到結構化數據,結合velocity模板生成sql,目前支持oracle和mysql兩個數據庫,兩個數據庫模板以下:

oracle
-- Create table
#foreach($item in $items)
create table $item.name.toUpperCase()
(
#foreach($column in $item.columns)
    #set($s = "#if($foreach.count != $item.columns.size()),#end")
    #set($s1 = "#if($column.defaultValue) default $column.defaultValue#end")
    $column.name.toUpperCase() $column.type.toUpperCase()$s1$s
#end
);
    #if($item.comment)

-- Add comments to the table
comment on table $item.name.toUpperCase()
is '$item.comment';
    #end

-- Add comments to the columns
#foreach($column in $item.columns)
comment on column $item.name.toUpperCase().$column.name.toUpperCase()
is '$column.comment';
#end

-- Create primary, unique and foreign key constraints
alter table $item.name.toUpperCase()
add constraint $item.name.toUpperCase()_PK primary key ($util.joinUpper($item.keys));

-- Create/Recreate indexes
#foreach($index in $item.indexs)
create unique $index.name on ($util.joinUpper($index.columns));
#end
#end
mysql
#foreach($item in $items)

create table $item.name
(
#foreach($column in $item.columns)
    #set($spliter = "#if($foreach.count != $item.columns.size()),#end")
    #set($defaultValue = "#if($column.defaultValue) default $column.defaultValue#end")
    #set($comment = "#if($column.comment) comment '$column.comment'#end")
    $column.name $column.type.toUpperCase()$defaultValue$comment$spliter
#end
);
#if($item.comment)

-- Add comments to the table
ALTER TABLE $item.name COMMENT '$item.comment';
#end

-- Create primary
alter table $item.name add primary key ($util.join($item.keys));

-- Create indexes
#foreach($index in $item.indexs)
create index $index.name on ${item.name}($util.join($index.columns));
#end
#end

爲了使工具更加好用,默認從剪貼板裏讀取markdown文件,生成後除了輸出控制檯外,還將內容放入剪貼板,在源碼bin目錄下已經生成了一個客戶端sqlmd.jar,你只需將符合上面規則的markdown複製到剪貼板,而後運行該客戶端,便可獲得最終的sql,命令以下

java -jar sqlmd.jar [oracle|mysql]

默認生成oracle的腳本,你能夠在命令後面加上mysql指定mysql

藉助commonmark咱們能夠很方便完成對markdown的解析,再結合velocity就能夠達到咱們想要的效果,用很低的成本就完成了一件很cool的事。

寫在最後

除了sql,咱們還能作什麼事,打開了這個潘多拉之盒,咱們能作的事取決於咱們的想象,我在以前的文章自動化單元測試的構想中裏提過,但願可以藉助markdown編寫測試用例,當時拍腦殼想了一個語法

# [config]

- casecount:100
- level:10

# [object]MpaasUser


# [class]MpaasQuery

## eq
- position:first
- rand:0%
- times:1-100

> field
- type:string
- value:rand/static
- valueType:raw/normal

可以實現嗎?徹底能夠的。再發散下思惟,還能幹什麼事?我最終的目的就是想用markdown構建整個系統的基礎框架,包括前端,後段,數據庫,測試用例,這個想法最先來源於藉助docsify完成倚天的文檔,我發現,我只要寫markdown就能完成一個很酷,很漂亮的文檔庫,整個文檔庫我只花了一週就完成,並且仍是業餘時間,那爲何不能用markdown來完成完整系統的構建呢?

參考

相關文章
相關標籤/搜索