我在大量Nodejs開發實踐中,發現回滾是一個很是嚴謹的話題,咱們應該重視這個回滾話題。咱們不能祈禱上天程序不要出錯,而忽略掉錯誤處理方案。javascript
好比,咱們在開發一個發佈系統的過程當中,有一系列的操做,數據庫CRUD,FS操做項目文件,同時對gitlab的api進行操做。這個時候咱們的順序多是這樣的:java
project_${id}
咱們來腦補下場景:mysql
那麼咱們就多麼尷尬啊。固然,咱們能夠經過捕獲錯誤來進行相對應的錯誤處理。可是咱們不知道咱們會在哪一步出現而回滾對應的行爲。通過個人總結,提出3種回滾模式:git
咱們須要創建一套任務機制,在此機制上面實現2個概念:github
咱們來看下如下的內容。redis
說到任務機制,咱們天然會想到以下的模式:sql
const task = new Tasker();
task.add(async () => {
await mysql.add({
a: 1,
b: 2
})
});
task.add(async () => {
fs.writeFileSync('/a', 'aaaaaa', 'utf8');
});
// ....
await task.run();
複製代碼
對,其實想法都是很是正確,再結合咱們提出的概念,就變成了以下的寫法:shell
task.add(async function resolve() {
fs.writeFileSync('/a', 'aaaaaa', 'utf8');
}, async function reject() {
fs.unlinkSync('/a');
})
複製代碼
確實咱們是實現了簡單的任務機制。可是咱們是否以爲這樣的寫法很是麻煩,那麼咱們將引出咱們今天的重點模塊 ys-dbo數據庫
咱們先來看一段代碼:npm
const DBO = require('ys-dbo');
const dbo = new DBO();
// 這裏咱們假設已經安裝了mysql模塊
dbo.until(async thread => {
// 咱們把以前的代碼實現一下
const file = '/tmp/test.txt';
await mysql.begin();
await mysql.insert('table', {
a: 1,
b: 2
});
fs.writeFileSync(file, 'aaaaaa', 'utf8');
thread.on('beforeRollback', async () => fs.unlinkSync(file));
gitlab.fork('project');
thread.on('beforeRollback', async () => gitlab.deleteProject('project'));
}).then(...).catch(...)
複製代碼
從上面代碼中咱們徹底能夠看出沒有任何task.add
的痕跡,取而代之的是beforeRollback
或者afterRollback
等事件。咱們經過action+event
的模式將任務機制簡化了。
因此咱們能夠看一個圖:
上圖明確描述了回滾的機制,咱們經過一一對應註冊的模式,來管理任務隊列。
我如今發現不少同窗不愛用回滾,可能嫌棄比較麻煩的寫法,這樣寫出來的代碼兼容性不會太好。可是咱們要知道回滾實際上是數據處於一致性狀態的重要手段。咱們要重視回滾,不在祈禱上天不要出錯。
在咱們公司,我也問過不少java開發的同窗,不多有人用到回滾,我就很納悶,做爲一位開發工程師,不考慮嚴謹模式,這是不合格的,回滾也能夠看出一個工程師的代碼素養。
你們不用刻意在乎這個模塊,畢竟是我的開發實踐出來的模塊,可能完善度不是很高,可是我會一直維護下去,由於畢竟本身的工做中也經常使用到。
npm i ys-dbo
複製代碼
喜歡的同窗點個贊吧,感謝!