自拍偷在线精品自拍偷,亚洲欧美中文日韩v在线观看不卡

字節(jié)一面:事務(wù)還沒提交的時(shí)候,Redolog 能不能被持久化到磁盤呢?

存儲(chǔ) 存儲(chǔ)軟件
每個(gè)線程都有自己 binlog cache 區(qū)域,在事務(wù)運(yùn)行的過程中,MySQL 會(huì)先把日志寫到 binlog cache 中,等到事務(wù)真正提交的時(shí)候,再統(tǒng)一把 binlog cache 中的數(shù)據(jù)寫到 binlog 文件中。(binlog cache 有很多個(gè),binlog 文件只有一個(gè)!)

又是被自己菜醒的一天,總結(jié)面經(jīng)看到這題目聽都沒聽過,打開百度就像吃飯一樣自然

老規(guī)矩,背誦版在文末。點(diǎn)擊閱讀原文可以直達(dá)我收錄整理的各大廠面試真題

首先,咱需要明白的是,啥是持久化?

聽起來高大上,換句簡(jiǎn)單的話來說,就是把數(shù)據(jù)寫到磁盤上,也成為落盤。

那為啥要做持久化到磁盤?

目的就是可以在數(shù)據(jù)丟失后進(jìn)行恢復(fù),保證數(shù)據(jù)不丟失。

那么對(duì)于 MySQL 來說,只要 binlog 和 redolog 都能正確持久化到磁盤上,就可以保證數(shù)據(jù)不丟失了。

由此引出文題,不過在講 redolog 之前,我們還是有必要先來說一下 binlog 的持久化操作。

binlog 持久化

這里引入了一個(gè)新的概念:binlog cache

從名字就能看出來,binlog cache 其實(shí)就是一片內(nèi)存區(qū)域,充當(dāng)緩存的作用。

每個(gè)線程都有自己 binlog cache 區(qū)域,在事務(wù)運(yùn)行的過程中,MySQL 會(huì)先把日志寫到 binlog cache 中,等到事務(wù)真正提交的時(shí)候,再統(tǒng)一把 binlog cache 中的數(shù)據(jù)寫到 binlog 文件中。(binlog cache 有很多個(gè),binlog 文件只有一個(gè)!)

事實(shí)上,這個(gè)從 binlog cache 寫到 binlog 文件中的操作,并不就是落盤操作了,這里僅僅是把 binlog 寫到了文件系統(tǒng)的 page cache 上(這一步對(duì)應(yīng)下圖中的 write 操作)。

簡(jiǎn)單解釋下文件系統(tǒng)的 page cache:

CPU 如果要訪問外部磁盤上的文件,需要首先將這些文件的內(nèi)容拷貝到內(nèi)存中,由于硬件的限制,從磁盤到內(nèi)存的數(shù)據(jù)傳輸速度是很慢的,如果現(xiàn)在物理內(nèi)存有空余,干嘛不用這些空閑內(nèi)存來緩存一些磁盤的文件內(nèi)容呢,這部分用作緩存磁盤文件的內(nèi)存就叫做 page cache。

很多同學(xué)看到這里可能覺得特別特別熟悉,是的,和 CPU 里的高速緩存是不是很像?兩者其實(shí)都是利用的局部性原理,只不過高速緩存是 CPU 緩存內(nèi)存的數(shù)據(jù),而 page cache 是內(nèi)存緩存磁盤的數(shù)據(jù),這也體現(xiàn)了操作系統(tǒng)內(nèi)存層次結(jié)構(gòu)分級(jí)的思想。

所以,最后需要把 page cache 中的數(shù)據(jù)同步到磁盤上,才算真正完成了 binlog 的持久化(這一步對(duì)應(yīng)下圖中的 fsync 操作)。一般情況下,我們認(rèn)為 fsync 才占磁盤的 IOPS (Input/Output Operations Per Second)

write 和 fsync 的時(shí)機(jī),是由參數(shù) sync_binlog 控制的:

  • sync_binlog = 0,每次提交事務(wù)的時(shí)候,只進(jìn)行 write,不進(jìn)行 fsync
  • sync_binlog = 1候,每次提交事務(wù)的時(shí)候,執(zhí)行 write 和 fsync
  • sync_binlog = N(N>1),每次提交事務(wù)的時(shí)候,執(zhí)行 write,累積 N 個(gè)事務(wù)后再執(zhí)行 fsync

可以看出來,如果業(yè)務(wù)場(chǎng)景涉及到的 IO 操作很多的話,可以適當(dāng)增大 sync_binlog 的值,提高性能。但是也存在一定的風(fēng)險(xiǎn),比如你設(shè)置成 100,萬一在第 80 個(gè)事務(wù)提交的時(shí)候數(shù)據(jù)庫(kù)宕機(jī)了,那這些事務(wù)的 binlog 日志由于沒有執(zhí)行 fsync,也就丟失了。

redolog 持久化

類比 binlog,在事務(wù)執(zhí)行過程中,binlog 都是存在 binlog cache 中,redolog 也有這樣一塊內(nèi)存區(qū)域,叫作 redolog buffer。

在事務(wù)運(yùn)行的過程中,MySQL 會(huì)先把日志寫到 redolog buffer 中,等到事務(wù)真正提交的時(shí)候,再統(tǒng)一把 redolog buffer 中的數(shù)據(jù)寫到 redolog 文件中。和 binlog 的落盤操作一樣,這個(gè)從 redolog buffer 寫到 redolog 文件中的操作,并不就是落盤操作了,這里僅僅是把 redolog 寫到了文件系統(tǒng)的 page cache 上,最后還需要執(zhí)行 fsync 才能夠?qū)崿F(xiàn)真正的落盤。

解釋下 redo log buffer?

在一個(gè)事務(wù)的更新過程中,日志是要寫多次的。比如下面這個(gè)事務(wù):

  1. begin
  2.  insert into table1 ... 
  3.  insert into table2 ... 
  4. commit

這個(gè)事務(wù)要往兩個(gè)表 table1 和 table2 中插入記錄,為了確保這個(gè)事務(wù)不被拆開,一次性的完整寫入日志文件中,在插入數(shù)據(jù)的過程中,我們需要把生成的日志都先保存起來。redolog buffer 就是這么一個(gè)用來先存 redo 日志的地方。

也就是說,在執(zhí)行第一條 insert 語句的時(shí)候,redolog buffer 也就寫入了這條記錄的日志。

不同于 binlog cache 每個(gè)線程都有一個(gè),redolog buffer 只有那么一個(gè)。

事實(shí)上,日志寫到 redolog buffer 是很快的,wirte 到 page cache 也差不多,但是 fsync 持久化到磁盤的速度就慢多了,為了控制 redo log 的寫入策略,InnoDB 提供了 innodb_flush_log_at_trx_commit 參數(shù),它有三種可能取值:

  • innodb_flush_log_at_trx_commit = 0,每次事務(wù)提交的時(shí)候,都只是把 redolog 留在 redolog buffer 中
  • innodb_flush_log_at_trx_commit = 1,每次事務(wù)提交的時(shí)候,都執(zhí)行 fsync 將 redolog 直接持久化到磁盤
  • innodb_flush_log_at_trx_commit = 2,每次事務(wù)提交的時(shí)候,都只執(zhí)行 write 將 redolog 寫到文件系統(tǒng)的 page cache 中
  • 說了這么多,各位小伙伴們對(duì) binlog 和 redolog 的持久化機(jī)制想必都有所了解了,我們來看文題:事務(wù)還沒提交的時(shí)候,redolog 能不能被持久化到磁盤呢?

先說答案,答案就是有可能。

分析下 redolog 可能存在的三種狀態(tài)(binlog 也差不多):

  • 事務(wù)執(zhí)行過程中,存在 MySQL 的進(jìn)程內(nèi)存中的 redolog buffer 中
  • 事務(wù)提交,執(zhí)行 write 操作存在文件系統(tǒng)的 page cache 中,但是沒有執(zhí)行 fsync 操作持久化到磁盤
  • 事務(wù)提交,執(zhí)行 fsync 操作持久化到磁盤

至于為什么說事務(wù)還沒提交的時(shí)候,redolog 也有可能被持久化到磁盤呢?

InnoDB 有一個(gè)后臺(tái)線程,每隔 1 秒輪詢一次,具體的操作是這樣的:調(diào)用 write 將 redolog buffer 中的日志寫到文件系統(tǒng)的 page cache,然后調(diào)用 fsync 持久化到磁盤。而在事務(wù)執(zhí)行中間過程的 redolog 都是直接寫在 redolog buffer 中的,也就是說,一個(gè)沒有提交的事務(wù)的 redolog,也是有可能會(huì)被后臺(tái)線程一起持久化到磁盤的。

另外,除了后臺(tái)線程每秒一次的輪詢操作外,還有兩種場(chǎng)景會(huì)讓一個(gè)沒有提交的事務(wù)的 redolog 寫盤:

  • innodb_flush_log_at_trx_commit 設(shè)置是 1,這樣并行的某個(gè)事務(wù)提交的時(shí)候,就會(huì)順帶將這個(gè)事務(wù)的 redolog buffer 持久化到磁盤

舉個(gè)例子,假設(shè)事務(wù) A 執(zhí)行到一半,已經(jīng)寫了一些 redolog 到 redolog buffer 中,這時(shí)候有另外一個(gè)事務(wù) B 提交,按照 innodb_flush_log_at_trx_commit = 1 的邏輯,事務(wù) B 要把 redolog buffer 里的日志全部持久化到磁盤,這時(shí)候,就會(huì)帶上事務(wù) A 在 redolog buffer 里的日志一起持久化到磁盤

  • redo log buffer 占用的空間達(dá)到 redolo buffer 大小(由參數(shù) innodb_log_buffer_size 控制,默認(rèn)是 8MB)一半的時(shí)候,后臺(tái)線程會(huì)主動(dòng)寫盤。不過由于這個(gè)事務(wù)并沒有提交,所以這個(gè)寫盤動(dòng)作只是 write 到了文件系統(tǒng)的 page cache,仍然是在內(nèi)存中,并沒有調(diào)用 fsync 真正落盤

最后放上這道題的背誦版:

  • 面試官:
  • 問題:事務(wù)還沒提交的時(shí)候,redo log 能不能被持久化到磁盤呢?

相關(guān)問題:MySQL 是如何保證數(shù)據(jù)不丟失的呢?

 小牛肉:事務(wù)還沒有提交的時(shí)候,redo log 是有可能被持久化到磁盤的。

redolog 的具體落盤操作是這樣的:在事務(wù)運(yùn)行的過程中,MySQL 會(huì)先把日志寫到 redolog buffer 中,等到事務(wù)真正提交的時(shí)候,再統(tǒng)一把 redolog buffer 中的數(shù)據(jù)寫到 redolog 文件中。不過這個(gè)從 redolog buffer 寫到 redolog 文件中的操作也就是 write 并不就是落盤操作了,這里僅僅是把 redolog 寫到了文件系統(tǒng)的 page cache 上,最后還需要執(zhí)行 fsync 才能夠?qū)崿F(xiàn)真正的落盤。

也就是說,redolog 其實(shí)存在三種狀態(tài):

  • 事務(wù)執(zhí)行過程中,存在 MySQL 的進(jìn)程內(nèi)存中的 redolog buffer 中
  • 事務(wù)提交,執(zhí)行 write 操作存在文件系統(tǒng)的 page cache 中,但是沒有執(zhí)行 fsync 操作持久化到磁盤
  • 事務(wù)提交,執(zhí)行 fsync 操作持久化到磁盤

額為什么說事務(wù)還沒提交的時(shí)候,redolog 也有可能被持久化到磁盤呢?

主要有三種可能的原因:

 

  • 第一種情況:InnoDB 有一個(gè)后臺(tái)線程,每隔 1 秒輪詢一次,具體的操作是這樣的:調(diào)用 write 將 redolog buffer 中的日志寫到文件系統(tǒng)的 page cache,然后調(diào)用 fsync 持久化到磁盤。而在事務(wù)執(zhí)行中間過程的 redolog 都是直接寫在 redolog buffer 中的,也就是說,一個(gè)沒有提交的事務(wù)的 redolog,也是有可能會(huì)被后臺(tái)線程一起持久化到磁盤的。
  • 第二種情況:innodb_flush_log_at_trx_commit 設(shè)置是 1,這個(gè)參數(shù)的意思就是,每次事務(wù)提交的時(shí)候,都執(zhí)行 fsync 將 redolog 直接持久化到磁盤(還有 0 和 2 的選擇,0 表示每次事務(wù)提交的時(shí)候,都只是把 redolog 留在 redolog buffer 中;2 表示每次事務(wù)提交的時(shí)候,都只執(zhí)行 write 將 redolog 寫到文件系統(tǒng)的 page cache 中)。舉個(gè)例子,假設(shè)事務(wù) A 執(zhí)行到一半,已經(jīng)寫了一些 redolog 到 redolog buffer 中,這時(shí)候有另外一個(gè)事務(wù) B 提交,按照 innodb_flush_log_at_trx_commit = 1 的邏輯,事務(wù) B 要把 redolog buffer 里的日志全部持久化到磁盤,這時(shí)候,就會(huì)帶上事務(wù) A 在 redolog buffer 里的日志一起持久化到磁盤
  • 第三種情況:redo log buffer 占用的空間達(dá)到 redolo buffer 大小(由參數(shù) innodb_log_buffer_size 控制,默認(rèn)是 8MB)一半的時(shí)候,后臺(tái)線程會(huì)主動(dòng)寫盤。不過由于這個(gè)事務(wù)并沒有提交,所以這個(gè)寫盤動(dòng)作只是 write 到了文件系統(tǒng)的 page cache,仍然是在內(nèi)存中,并沒有調(diào)用 fsync 真正落盤

 

責(zé)任編輯:武曉燕 來源: 飛天小牛肉
相關(guān)推薦

2024-01-02 07:55:26

MySQLRedolog緩存

2024-11-11 10:34:55

2022-03-30 10:10:17

字節(jié)碼??臻g

2022-12-27 17:40:57

意向鎖MySQLInnoDB

2022-08-13 12:07:14

URLHTTP加密

2021-06-15 11:33:48

監(jiān)控微信聊天前端

2024-09-19 08:51:01

HTTP解密截取

2024-11-26 08:52:34

SQL優(yōu)化Kafka

2022-10-10 08:13:16

遞歸通用代碼

2022-05-10 22:00:41

UDPTCP協(xié)議

2022-01-05 21:54:51

網(wǎng)絡(luò)分層系統(tǒng)

2022-11-30 17:13:05

MySQLDynamic存儲(chǔ)

2019-11-21 09:25:23

AI 數(shù)據(jù)人工智能

2021-05-08 11:32:42

監(jiān)控信聊天

2022-10-19 14:08:42

SYNTCP報(bào)文

2022-12-13 18:09:25

連接狀態(tài)客戶端

2022-08-18 17:44:25

HTTPS協(xié)議漏洞

2022-06-01 11:52:42

網(wǎng)站客戶端網(wǎng)絡(luò)

2010-04-13 10:02:16

索引

2016-05-19 17:10:27

銀行
點(diǎn)贊
收藏

51CTO技術(shù)棧公眾號(hào)