captions-utils.ts 1.7 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152
  1. import { createReadStream, createWriteStream } from 'fs'
  2. import { move, remove } from 'fs-extra/esm'
  3. import { Transform } from 'stream'
  4. import { MVideoCaption } from '@server/types/models/index.js'
  5. import { pipelinePromise } from './core-utils.js'
  6. async function moveAndProcessCaptionFile (physicalFile: { filename?: string, path: string }, videoCaption: MVideoCaption) {
  7. const destination = videoCaption.getFSPath()
  8. // Convert this srt file to vtt
  9. if (physicalFile.path.endsWith('.srt')) {
  10. await convertSrtToVtt(physicalFile.path, destination)
  11. await remove(physicalFile.path)
  12. } else if (physicalFile.path !== destination) { // Just move the vtt file
  13. await move(physicalFile.path, destination, { overwrite: true })
  14. }
  15. // This is important in case if there is another attempt in the retry process
  16. if (physicalFile.filename) physicalFile.filename = videoCaption.filename
  17. physicalFile.path = destination
  18. }
  19. // ---------------------------------------------------------------------------
  20. export {
  21. moveAndProcessCaptionFile
  22. }
  23. // ---------------------------------------------------------------------------
  24. async function convertSrtToVtt (source: string, destination: string) {
  25. const fixVTT = new Transform({
  26. transform: (chunk, _encoding, cb) => {
  27. let block: string = chunk.toString()
  28. block = block.replace(/(\d\d:\d\d:\d\d)(\s)/g, '$1.000$2')
  29. .replace(/(\d\d:\d\d:\d\d),(\d)(\s)/g, '$1.00$2$3')
  30. .replace(/(\d\d:\d\d:\d\d),(\d\d)(\s)/g, '$1.0$2$3')
  31. return cb(undefined, block)
  32. }
  33. })
  34. const srt2vtt = await import('srt-to-vtt')
  35. return pipelinePromise(
  36. createReadStream(source),
  37. srt2vtt.default(),
  38. fixVTT,
  39. createWriteStream(destination)
  40. )
  41. }