@@ -15,6 +15,8 @@ const {
1515 canaryChannelLabel,
1616 rcNumber,
1717} = require ( '../../ReactVersions' ) ;
18+ const yargs = require ( 'yargs' ) ;
19+ const { buildEverything} = require ( './build-ghaction' ) ;
1820
1921// Runs the build script for both stable and experimental release channels,
2022// by configuring an environment variable.
@@ -51,44 +53,88 @@ fs.writeFileSync(
5153 `export default '${ PLACEHOLDER_REACT_VERSION } ';\n`
5254) ;
5355
54- if ( process . env . CIRCLE_NODE_TOTAL ) {
55- // In CI, we use multiple concurrent processes. Allocate half the processes to
56- // build the stable channel, and the other half for experimental. Override
57- // the environment variables to "trick" the underlying build script.
58- const total = parseInt ( process . env . CIRCLE_NODE_TOTAL , 10 ) ;
59- const halfTotal = Math . floor ( total / 2 ) ;
60- const index = parseInt ( process . env . CIRCLE_NODE_INDEX , 10 ) ;
61- if ( index < halfTotal ) {
62- const nodeTotal = halfTotal ;
63- const nodeIndex = index ;
64- buildForChannel ( 'stable' , nodeTotal , nodeIndex ) ;
65- processStable ( './build' ) ;
56+ const argv = yargs . wrap ( yargs . terminalWidth ( ) ) . options ( {
57+ releaseChannel : {
58+ alias : 'r' ,
59+ describe : 'Build the given release channel.' ,
60+ requiresArg : true ,
61+ type : 'string' ,
62+ choices : [ 'experimental' , 'stable' ] ,
63+ } ,
64+ index : {
65+ alias : 'i' ,
66+ describe : 'Worker id.' ,
67+ requiresArg : true ,
68+ type : 'number' ,
69+ } ,
70+ total : {
71+ alias : 't' ,
72+ describe : 'Total number of workers.' ,
73+ requiresArg : true ,
74+ type : 'number' ,
75+ } ,
76+ ci : {
77+ describe : 'Run tests in CI' ,
78+ requiresArg : false ,
79+ type : 'choices' ,
80+ choices : [ 'circleci' , 'github' ] ,
81+ } ,
82+ } ) . argv ;
83+
84+ async function main ( ) {
85+ if ( argv . ci === 'github' ) {
86+ await buildEverything ( argv . index , argv . total ) ;
87+ switch ( argv . releaseChannel ) {
88+ case 'stable' : {
89+ processStable ( './build' ) ;
90+ break ;
91+ }
92+ case 'experimental' : {
93+ processExperimental ( './build' ) ;
94+ break ;
95+ }
96+ default :
97+ throw new Error ( `Unknown release channel ${ argv . releaseChannel } ` ) ;
98+ }
99+ } else if ( argv . ci === 'circleci' ) {
100+ // In CI, we use multiple concurrent processes. Allocate half the processes to
101+ // build the stable channel, and the other half for experimental. Override
102+ // the environment variables to "trick" the underlying build script.
103+ const total = parseInt ( process . env . CIRCLE_NODE_TOTAL , 10 ) ;
104+ const halfTotal = Math . floor ( total / 2 ) ;
105+ const index = parseInt ( process . env . CIRCLE_NODE_INDEX , 10 ) ;
106+ if ( index < halfTotal ) {
107+ const nodeTotal = halfTotal ;
108+ const nodeIndex = index ;
109+ buildForChannel ( 'stable' , nodeTotal , nodeIndex ) ;
110+ processStable ( './build' ) ;
111+ } else {
112+ const nodeTotal = total - halfTotal ;
113+ const nodeIndex = index - halfTotal ;
114+ buildForChannel ( 'experimental' , nodeTotal , nodeIndex ) ;
115+ processExperimental ( './build' ) ;
116+ }
66117 } else {
67- const nodeTotal = total - halfTotal ;
68- const nodeIndex = index - halfTotal ;
69- buildForChannel ( 'experimental' , nodeTotal , nodeIndex ) ;
70- processExperimental ( './build' ) ;
118+ // Running locally, no concurrency. Move each channel's build artifacts into
119+ // a temporary directory so that they don't conflict.
120+ buildForChannel ( 'stable' , '' , '' ) ;
121+ const stableDir = tmp . dirSync ( ) . name ;
122+ crossDeviceRenameSync ( './build' , stableDir ) ;
123+ processStable ( stableDir ) ;
124+ buildForChannel ( 'experimental' , '' , '' ) ;
125+ const experimentalDir = tmp . dirSync ( ) . name ;
126+ crossDeviceRenameSync ( './build' , experimentalDir ) ;
127+ processExperimental ( experimentalDir ) ;
128+
129+ // Then merge the experimental folder into the stable one. processExperimental
130+ // will have already removed conflicting files.
131+ //
132+ // In CI, merging is handled automatically by CircleCI's workspace feature.
133+ mergeDirsSync ( experimentalDir + '/' , stableDir + '/' ) ;
134+
135+ // Now restore the combined directory back to its original name
136+ crossDeviceRenameSync ( stableDir , './build' ) ;
71137 }
72- } else {
73- // Running locally, no concurrency. Move each channel's build artifacts into
74- // a temporary directory so that they don't conflict.
75- buildForChannel ( 'stable' , '' , '' ) ;
76- const stableDir = tmp . dirSync ( ) . name ;
77- crossDeviceRenameSync ( './build' , stableDir ) ;
78- processStable ( stableDir ) ;
79- buildForChannel ( 'experimental' , '' , '' ) ;
80- const experimentalDir = tmp . dirSync ( ) . name ;
81- crossDeviceRenameSync ( './build' , experimentalDir ) ;
82- processExperimental ( experimentalDir ) ;
83-
84- // Then merge the experimental folder into the stable one. processExperimental
85- // will have already removed conflicting files.
86- //
87- // In CI, merging is handled automatically by CircleCI's workspace feature.
88- mergeDirsSync ( experimentalDir + '/' , stableDir + '/' ) ;
89-
90- // Now restore the combined directory back to its original name
91- crossDeviceRenameSync ( stableDir , './build' ) ;
92138}
93139
94140function buildForChannel ( channel , nodeTotal , nodeIndex ) {
@@ -455,3 +501,5 @@ function mergeDirsSync(source, destination) {
455501 }
456502 }
457503}
504+
505+ main ( ) ;
0 commit comments