rotatelogger_test.go 8.5 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330
  1. package logx
  2. import (
  3. "os"
  4. "path/filepath"
  5. "syscall"
  6. "testing"
  7. "time"
  8. "github.com/stretchr/testify/assert"
  9. "github.com/zeromicro/go-zero/core/fs"
  10. )
  11. func TestDailyRotateRuleMarkRotated(t *testing.T) {
  12. var rule DailyRotateRule
  13. rule.MarkRotated()
  14. assert.Equal(t, getNowDate(), rule.rotatedTime)
  15. }
  16. func TestDailyRotateRuleOutdatedFiles(t *testing.T) {
  17. var rule DailyRotateRule
  18. assert.Empty(t, rule.OutdatedFiles())
  19. rule.days = 1
  20. assert.Empty(t, rule.OutdatedFiles())
  21. rule.gzip = true
  22. assert.Empty(t, rule.OutdatedFiles())
  23. }
  24. func TestDailyRotateRuleShallRotate(t *testing.T) {
  25. var rule DailyRotateRule
  26. rule.rotatedTime = time.Now().Add(time.Hour * 24).Format(dateFormat)
  27. assert.True(t, rule.ShallRotate(0))
  28. }
  29. func TestSizeLimitRotateRuleMarkRotated(t *testing.T) {
  30. var rule SizeLimitRotateRule
  31. rule.MarkRotated()
  32. assert.Equal(t, getNowDateInRFC3339Format(), rule.rotatedTime)
  33. }
  34. func TestSizeLimitRotateRuleOutdatedFiles(t *testing.T) {
  35. var rule SizeLimitRotateRule
  36. assert.Empty(t, rule.OutdatedFiles())
  37. rule.days = 1
  38. assert.Empty(t, rule.OutdatedFiles())
  39. rule.gzip = true
  40. assert.Empty(t, rule.OutdatedFiles())
  41. rule.maxBackups = 0
  42. assert.Empty(t, rule.OutdatedFiles())
  43. }
  44. func TestSizeLimitRotateRuleShallRotate(t *testing.T) {
  45. var rule SizeLimitRotateRule
  46. rule.rotatedTime = time.Now().Add(time.Hour * 24).Format(fileTimeFormat)
  47. rule.maxSize = 0
  48. assert.False(t, rule.ShallRotate(0))
  49. rule.maxSize = 100
  50. assert.False(t, rule.ShallRotate(0))
  51. assert.True(t, rule.ShallRotate(101*megaBytes))
  52. }
  53. func TestRotateLoggerClose(t *testing.T) {
  54. filename, err := fs.TempFilenameWithText("foo")
  55. assert.Nil(t, err)
  56. if len(filename) > 0 {
  57. defer os.Remove(filename)
  58. }
  59. logger, err := NewLogger(filename, new(DailyRotateRule), false)
  60. assert.Nil(t, err)
  61. assert.Nil(t, logger.Close())
  62. }
  63. func TestRotateLoggerGetBackupFilename(t *testing.T) {
  64. filename, err := fs.TempFilenameWithText("foo")
  65. assert.Nil(t, err)
  66. if len(filename) > 0 {
  67. defer os.Remove(filename)
  68. }
  69. logger, err := NewLogger(filename, new(DailyRotateRule), false)
  70. assert.Nil(t, err)
  71. assert.True(t, len(logger.getBackupFilename()) > 0)
  72. logger.backup = ""
  73. assert.True(t, len(logger.getBackupFilename()) > 0)
  74. }
  75. func TestRotateLoggerMayCompressFile(t *testing.T) {
  76. old := os.Stdout
  77. os.Stdout = os.NewFile(0, os.DevNull)
  78. defer func() {
  79. os.Stdout = old
  80. }()
  81. filename, err := fs.TempFilenameWithText("foo")
  82. assert.Nil(t, err)
  83. if len(filename) > 0 {
  84. defer os.Remove(filename)
  85. }
  86. logger, err := NewLogger(filename, new(DailyRotateRule), false)
  87. assert.Nil(t, err)
  88. logger.maybeCompressFile(filename)
  89. _, err = os.Stat(filename)
  90. assert.Nil(t, err)
  91. }
  92. func TestRotateLoggerMayCompressFileTrue(t *testing.T) {
  93. old := os.Stdout
  94. os.Stdout = os.NewFile(0, os.DevNull)
  95. defer func() {
  96. os.Stdout = old
  97. }()
  98. filename, err := fs.TempFilenameWithText("foo")
  99. assert.Nil(t, err)
  100. logger, err := NewLogger(filename, new(DailyRotateRule), true)
  101. assert.Nil(t, err)
  102. if len(filename) > 0 {
  103. defer os.Remove(filepath.Base(logger.getBackupFilename()) + ".gz")
  104. }
  105. logger.maybeCompressFile(filename)
  106. _, err = os.Stat(filename)
  107. assert.NotNil(t, err)
  108. }
  109. func TestRotateLoggerRotate(t *testing.T) {
  110. filename, err := fs.TempFilenameWithText("foo")
  111. assert.Nil(t, err)
  112. logger, err := NewLogger(filename, new(DailyRotateRule), true)
  113. assert.Nil(t, err)
  114. if len(filename) > 0 {
  115. defer func() {
  116. os.Remove(logger.getBackupFilename())
  117. os.Remove(filepath.Base(logger.getBackupFilename()) + ".gz")
  118. }()
  119. }
  120. err = logger.rotate()
  121. switch v := err.(type) {
  122. case *os.LinkError:
  123. // avoid rename error on docker container
  124. assert.Equal(t, syscall.EXDEV, v.Err)
  125. case *os.PathError:
  126. // ignore remove error for tests,
  127. // files are cleaned in GitHub actions.
  128. assert.Equal(t, "remove", v.Op)
  129. default:
  130. assert.Nil(t, err)
  131. }
  132. }
  133. func TestRotateLoggerWrite(t *testing.T) {
  134. filename, err := fs.TempFilenameWithText("foo")
  135. assert.Nil(t, err)
  136. rule := new(DailyRotateRule)
  137. logger, err := NewLogger(filename, rule, true)
  138. assert.Nil(t, err)
  139. if len(filename) > 0 {
  140. defer func() {
  141. os.Remove(logger.getBackupFilename())
  142. os.Remove(filepath.Base(logger.getBackupFilename()) + ".gz")
  143. }()
  144. }
  145. // the following write calls cannot be changed to Write, because of DATA RACE.
  146. logger.write([]byte(`foo`))
  147. rule.rotatedTime = time.Now().Add(-time.Hour * 24).Format(dateFormat)
  148. logger.write([]byte(`bar`))
  149. logger.Close()
  150. logger.write([]byte(`baz`))
  151. }
  152. func TestLogWriterClose(t *testing.T) {
  153. assert.Nil(t, newLogWriter(nil).Close())
  154. }
  155. func TestRotateLoggerWithSizeLimitRotateRuleClose(t *testing.T) {
  156. filename, err := fs.TempFilenameWithText("foo")
  157. assert.Nil(t, err)
  158. if len(filename) > 0 {
  159. defer os.Remove(filename)
  160. }
  161. logger, err := NewLogger(filename, new(SizeLimitRotateRule), false)
  162. assert.Nil(t, err)
  163. assert.Nil(t, logger.Close())
  164. }
  165. func TestRotateLoggerGetBackupWithSizeLimitRotateRuleFilename(t *testing.T) {
  166. filename, err := fs.TempFilenameWithText("foo")
  167. assert.Nil(t, err)
  168. if len(filename) > 0 {
  169. defer os.Remove(filename)
  170. }
  171. logger, err := NewLogger(filename, new(SizeLimitRotateRule), false)
  172. assert.Nil(t, err)
  173. assert.True(t, len(logger.getBackupFilename()) > 0)
  174. logger.backup = ""
  175. assert.True(t, len(logger.getBackupFilename()) > 0)
  176. }
  177. func TestRotateLoggerWithSizeLimitRotateRuleMayCompressFile(t *testing.T) {
  178. old := os.Stdout
  179. os.Stdout = os.NewFile(0, os.DevNull)
  180. defer func() {
  181. os.Stdout = old
  182. }()
  183. filename, err := fs.TempFilenameWithText("foo")
  184. assert.Nil(t, err)
  185. if len(filename) > 0 {
  186. defer os.Remove(filename)
  187. }
  188. logger, err := NewLogger(filename, new(SizeLimitRotateRule), false)
  189. assert.Nil(t, err)
  190. logger.maybeCompressFile(filename)
  191. _, err = os.Stat(filename)
  192. assert.Nil(t, err)
  193. }
  194. func TestRotateLoggerWithSizeLimitRotateRuleMayCompressFileTrue(t *testing.T) {
  195. old := os.Stdout
  196. os.Stdout = os.NewFile(0, os.DevNull)
  197. defer func() {
  198. os.Stdout = old
  199. }()
  200. filename, err := fs.TempFilenameWithText("foo")
  201. assert.Nil(t, err)
  202. logger, err := NewLogger(filename, new(SizeLimitRotateRule), true)
  203. assert.Nil(t, err)
  204. if len(filename) > 0 {
  205. defer os.Remove(filepath.Base(logger.getBackupFilename()) + ".gz")
  206. }
  207. logger.maybeCompressFile(filename)
  208. _, err = os.Stat(filename)
  209. assert.NotNil(t, err)
  210. }
  211. func TestRotateLoggerWithSizeLimitRotateRuleRotate(t *testing.T) {
  212. filename, err := fs.TempFilenameWithText("foo")
  213. assert.Nil(t, err)
  214. logger, err := NewLogger(filename, new(SizeLimitRotateRule), true)
  215. assert.Nil(t, err)
  216. if len(filename) > 0 {
  217. defer func() {
  218. os.Remove(logger.getBackupFilename())
  219. os.Remove(filepath.Base(logger.getBackupFilename()) + ".gz")
  220. }()
  221. }
  222. err = logger.rotate()
  223. switch v := err.(type) {
  224. case *os.LinkError:
  225. // avoid rename error on docker container
  226. assert.Equal(t, syscall.EXDEV, v.Err)
  227. case *os.PathError:
  228. // ignore remove error for tests,
  229. // files are cleaned in GitHub actions.
  230. assert.Equal(t, "remove", v.Op)
  231. default:
  232. assert.Nil(t, err)
  233. }
  234. }
  235. func TestRotateLoggerWithSizeLimitRotateRuleWrite(t *testing.T) {
  236. filename, err := fs.TempFilenameWithText("foo")
  237. assert.Nil(t, err)
  238. rule := new(SizeLimitRotateRule)
  239. logger, err := NewLogger(filename, rule, true)
  240. assert.Nil(t, err)
  241. if len(filename) > 0 {
  242. defer func() {
  243. os.Remove(logger.getBackupFilename())
  244. os.Remove(filepath.Base(logger.getBackupFilename()) + ".gz")
  245. }()
  246. }
  247. // the following write calls cannot be changed to Write, because of DATA RACE.
  248. logger.write([]byte(`foo`))
  249. rule.rotatedTime = time.Now().Add(-time.Hour * 24).Format(dateFormat)
  250. logger.write([]byte(`bar`))
  251. logger.Close()
  252. logger.write([]byte(`baz`))
  253. }
  254. func BenchmarkRotateLogger(b *testing.B) {
  255. filename := "./test.log"
  256. filename2 := "./test2.log"
  257. dailyRotateRuleLogger, err1 := NewLogger(
  258. filename,
  259. DefaultRotateRule(
  260. filename,
  261. backupFileDelimiter,
  262. 1,
  263. true,
  264. ),
  265. true,
  266. )
  267. if err1 != nil {
  268. b.Logf("Failed to new daily rotate rule logger: %v", err1)
  269. b.FailNow()
  270. }
  271. sizeLimitRotateRuleLogger, err2 := NewLogger(
  272. filename2,
  273. NewSizeLimitRotateRule(
  274. filename,
  275. backupFileDelimiter,
  276. 1,
  277. 100,
  278. 10,
  279. true,
  280. ),
  281. true,
  282. )
  283. if err2 != nil {
  284. b.Logf("Failed to new size limit rotate rule logger: %v", err1)
  285. b.FailNow()
  286. }
  287. defer func() {
  288. dailyRotateRuleLogger.Close()
  289. sizeLimitRotateRuleLogger.Close()
  290. os.Remove(filename)
  291. os.Remove(filename2)
  292. }()
  293. b.Run("daily rotate rule", func(b *testing.B) {
  294. for i := 0; i < b.N; i++ {
  295. dailyRotateRuleLogger.write([]byte("testing\ntesting\n"))
  296. }
  297. })
  298. b.Run("size limit rotate rule", func(b *testing.B) {
  299. for i := 0; i < b.N; i++ {
  300. sizeLimitRotateRuleLogger.write([]byte("testing\ntesting\n"))
  301. }
  302. })
  303. }