ci-release-build.js 5.2 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173
  1. require('dotenv-safe').load()
  2. const assert = require('assert')
  3. const request = require('request')
  4. const buildAppVeyorURL = 'https://windows-ci.electronjs.org/api/builds'
  5. const appVeyorJobs = {
  6. 'electron-x64': 'electron',
  7. 'electron-ia32': 'electron-39ng6'
  8. }
  9. const circleCIJobs = [
  10. 'electron-linux-arm',
  11. 'electron-linux-arm64',
  12. 'electron-linux-ia32',
  13. 'electron-linux-x64',
  14. 'electron-osx-x64',
  15. 'electron-mas-x64'
  16. ]
  17. async function makeRequest (requestOptions, parseResponse) {
  18. return new Promise((resolve, reject) => {
  19. request(requestOptions, (err, res, body) => {
  20. if (!err && res.statusCode >= 200 && res.statusCode < 300) {
  21. if (parseResponse) {
  22. const build = JSON.parse(body)
  23. resolve(build)
  24. } else {
  25. resolve(body)
  26. }
  27. } else {
  28. console.error('Error occurred while requesting:', requestOptions.url)
  29. if (parseResponse) {
  30. try {
  31. console.log('Error: ', `(status ${res.statusCode})`, err || JSON.parse(res.body), requestOptions)
  32. } catch (err) {
  33. console.log('Error: ', `(status ${res.statusCode})`, err || res.body, requestOptions)
  34. }
  35. } else {
  36. console.log('Error: ', `(status ${res.statusCode})`, err || res.body, requestOptions)
  37. }
  38. reject(err)
  39. }
  40. })
  41. })
  42. }
  43. async function circleCIcall (buildUrl, targetBranch, job, options) {
  44. console.log(`Triggering CircleCI to run build job: ${job} on branch: ${targetBranch} with release flag.`)
  45. let buildRequest = {
  46. 'build_parameters': {
  47. 'CIRCLE_JOB': job
  48. }
  49. }
  50. if (options.ghRelease) {
  51. buildRequest.build_parameters.ELECTRON_RELEASE = 1
  52. } else {
  53. buildRequest.build_parameters.RUN_RELEASE_BUILD = 'true'
  54. }
  55. if (options.automaticRelease) {
  56. buildRequest.build_parameters.AUTO_RELEASE = 'true'
  57. }
  58. let circleResponse = await makeRequest({
  59. method: 'POST',
  60. url: buildUrl,
  61. headers: {
  62. 'Content-Type': 'application/json',
  63. 'Accept': 'application/json'
  64. },
  65. body: JSON.stringify(buildRequest)
  66. }, true).catch(err => {
  67. console.log('Error calling CircleCI:', err)
  68. })
  69. console.log(`CircleCI release build request for ${job} successful. Check ${circleResponse.build_url} for status.`)
  70. }
  71. function buildAppVeyor (targetBranch, options) {
  72. const validJobs = Object.keys(appVeyorJobs)
  73. if (options.job) {
  74. assert(validJobs.includes(options.job), `Unknown AppVeyor CI job name: ${options.job}. Valid values are: ${validJobs}.`)
  75. callAppVeyor(targetBranch, options.job, options)
  76. } else {
  77. validJobs.forEach((job) => callAppVeyor(targetBranch, job, options))
  78. }
  79. }
  80. async function callAppVeyor (targetBranch, job, options) {
  81. console.log(`Triggering AppVeyor to run build job: ${job} on branch: ${targetBranch} with release flag.`)
  82. let environmentVariables = {}
  83. if (options.ghRelease) {
  84. environmentVariables.ELECTRON_RELEASE = 1
  85. } else {
  86. environmentVariables.RUN_RELEASE_BUILD = 'true'
  87. }
  88. if (options.automaticRelease) {
  89. environmentVariables.AUTO_RELEASE = 'true'
  90. }
  91. const requestOpts = {
  92. url: buildAppVeyorURL,
  93. auth: {
  94. bearer: process.env.APPVEYOR_TOKEN
  95. },
  96. headers: {
  97. 'Content-Type': 'application/json'
  98. },
  99. body: JSON.stringify({
  100. accountName: 'AppVeyor',
  101. projectSlug: appVeyorJobs[job],
  102. branch: targetBranch,
  103. environmentVariables
  104. }),
  105. method: 'POST'
  106. }
  107. let appVeyorResponse = await makeRequest(requestOpts, true).catch(err => {
  108. console.log('Error calling AppVeyor:', err)
  109. })
  110. const buildUrl = `https://windows-ci.electronjs.org/project/AppVeyor/${appVeyorJobs[job]}/build/${appVeyorResponse.version}`
  111. console.log(`AppVeyor release build request for ${job} successful. Check build status at ${buildUrl}`)
  112. }
  113. function buildCircleCI (targetBranch, options) {
  114. const circleBuildUrl = `https://circleci.com/api/v1.1/project/github/electron/electron/tree/${targetBranch}?circle-token=${process.env.CIRCLE_TOKEN}`
  115. if (options.job) {
  116. assert(circleCIJobs.includes(options.job), `Unknown CircleCI job name: ${options.job}. Valid values are: ${circleCIJobs}.`)
  117. circleCIcall(circleBuildUrl, targetBranch, options.job, options)
  118. } else {
  119. circleCIJobs.forEach((job) => circleCIcall(circleBuildUrl, targetBranch, job, options))
  120. }
  121. }
  122. function runRelease (targetBranch, options) {
  123. if (options.ci) {
  124. switch (options.ci) {
  125. case 'CircleCI': {
  126. buildCircleCI(targetBranch, options)
  127. break
  128. }
  129. case 'AppVeyor': {
  130. buildAppVeyor(targetBranch, options)
  131. break
  132. }
  133. default: {
  134. console.log(`Error! Unknown CI: ${options.ci}.`)
  135. process.exit(1)
  136. }
  137. }
  138. } else {
  139. buildCircleCI(targetBranch, options)
  140. buildAppVeyor(targetBranch, options)
  141. }
  142. }
  143. module.exports = runRelease
  144. if (require.main === module) {
  145. const args = require('minimist')(process.argv.slice(2), {
  146. boolean: ['ghRelease', 'automaticRelease']
  147. })
  148. const targetBranch = args._[0]
  149. if (args._.length < 1) {
  150. console.log(`Trigger CI to build release builds of electron.
  151. Usage: ci-release-build.js [--job=CI_JOB_NAME] [--ci=CircleCI|AppVeyor] [--ghRelease] [--automaticRelease] TARGET_BRANCH
  152. `)
  153. process.exit(0)
  154. }
  155. runRelease(targetBranch, args)
  156. }