version-utils.js 2.9 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899
  1. const path = require('path')
  2. const fs = require('fs')
  3. const semver = require('semver')
  4. const { GitProcess } = require('dugite')
  5. const { promisify } = require('util')
  6. const { ELECTRON_DIR } = require('../lib/utils')
  7. const readFile = promisify(fs.readFile)
  8. const preType = {
  9. NONE: 'none',
  10. PARTIAL: 'partial',
  11. FULL: 'full'
  12. }
  13. const getCurrentDate = () => {
  14. const d = new Date()
  15. const dd = `${d.getDate()}`.padStart(2, '0')
  16. const mm = `${d.getMonth() + 1}`.padStart(2, '0')
  17. const yyyy = d.getFullYear()
  18. return `${yyyy}${mm}${dd}`
  19. }
  20. const isNightly = v => v.includes('nightly')
  21. const isBeta = v => v.includes('beta')
  22. const isStable = v => {
  23. const parsed = semver.parse(v)
  24. return !!(parsed && parsed.prerelease.length === 0)
  25. }
  26. const makeVersion = (components, delim, pre = preType.NONE) => {
  27. let version = [components.major, components.minor, components.patch].join(delim)
  28. if (pre === preType.PARTIAL) {
  29. version += `${delim}${components.pre[1] || 0}`
  30. } else if (pre === preType.FULL) {
  31. version += `-${components.pre[0]}${delim}${components.pre[1]}`
  32. }
  33. return version
  34. }
  35. async function nextBeta (v) {
  36. const next = semver.coerce(semver.clean(v))
  37. const tagBlob = await GitProcess.exec(['tag', '--list', '-l', `v${next}-beta.*`], ELECTRON_DIR)
  38. const tags = tagBlob.stdout.split('\n').filter(e => e !== '')
  39. tags.sort((t1, t2) => semver.gt(t1, t2))
  40. // increment the latest existing beta tag or start at beta.1 if it's a new beta line
  41. return tags.length === 0 ? `${next}-beta.1` : semver.inc(tags.pop(), 'prerelease')
  42. }
  43. async function getElectronVersion () {
  44. const versionPath = path.resolve(ELECTRON_DIR, 'ELECTRON_VERSION')
  45. const version = await readFile(versionPath, 'utf8')
  46. return version.trim()
  47. }
  48. async function nextNightly (v) {
  49. let next = semver.valid(semver.coerce(v))
  50. const pre = `nightly.${getCurrentDate()}`
  51. const branch = (await GitProcess.exec(['rev-parse', '--abbrev-ref', 'HEAD'], ELECTRON_DIR)).stdout.trim()
  52. if (branch === 'master') {
  53. next = semver.inc(await getLastMajorForMaster(), 'major')
  54. } else if (isStable(v)) {
  55. next = semver.inc(next, 'patch')
  56. }
  57. return `${next}-${pre}`
  58. }
  59. async function getLastMajorForMaster () {
  60. let branchNames
  61. const result = await GitProcess.exec(['branch', '-a', '--remote', '--list', 'origin/[0-9]-[0-9]-x'], ELECTRON_DIR)
  62. if (result.exitCode === 0) {
  63. branchNames = result.stdout.trim().split('\n')
  64. const filtered = branchNames.map(b => b.replace('origin/', ''))
  65. return getNextReleaseBranch(filtered)
  66. } else {
  67. throw new Error('Release branches could not be fetched.')
  68. }
  69. }
  70. function getNextReleaseBranch (branches) {
  71. const converted = branches.map(b => b.replace(/-/g, '.').replace('x', '0'))
  72. return converted.reduce((v1, v2) => semver.gt(v1, v2) ? v1 : v2)
  73. }
  74. module.exports = {
  75. isStable,
  76. isBeta,
  77. isNightly,
  78. nextBeta,
  79. makeVersion,
  80. getElectronVersion,
  81. nextNightly,
  82. preType
  83. }