@@ -8,6 +8,43 @@ const { readPackageJson, getPackageName } = require('./utils/package-updater');
88const { buildPackage, testPackage, publishPackage } = require ( './utils/publisher' ) ;
99const { stageFiles, commit } = require ( './utils/git-handler' ) ;
1010
11+ // Parse command line arguments
12+ const args = process . argv . slice ( 2 ) ;
13+
14+ function getSkippedPackageNames ( cliArgs ) {
15+ const skippedPackageNames = new Set ( ) ;
16+
17+ for ( let i = 0 ; i < cliArgs . length ; i ++ ) {
18+ const arg = cliArgs [ i ] ;
19+
20+ if ( arg === '--skip' && cliArgs [ i + 1 ] ) {
21+ const listArg = cliArgs [ i + 1 ] ;
22+ listArg
23+ . split ( ',' )
24+ . map ( item => item . trim ( ) )
25+ . filter ( Boolean )
26+ . forEach ( item => skippedPackageNames . add ( item ) ) ;
27+ i += 1 ;
28+ continue ;
29+ }
30+
31+ if ( arg . startsWith ( '--skip=' ) ) {
32+ arg
33+ . slice ( '--skip=' . length )
34+ . split ( ',' )
35+ . map ( item => item . trim ( ) )
36+ . filter ( Boolean )
37+ . forEach ( item => skippedPackageNames . add ( item ) ) ;
38+ }
39+
40+ if ( arg === '--skip-root' ) {
41+ skippedPackageNames . add ( 'root' ) ;
42+ }
43+ }
44+
45+ return skippedPackageNames ;
46+ }
47+
1148// Paths
1249const rootDir = path . join ( __dirname , '..' ) ;
1350const rootPackageJsonPath = path . join ( rootDir , 'package.json' ) ;
@@ -73,56 +110,100 @@ async function main() {
73110
74111 const releaseState = JSON . parse ( fs . readFileSync ( stateFilePath , 'utf8' ) ) ;
75112 const { version, packages } = releaseState ;
113+ const rootPackage = readPackageJson ( rootPackageJsonPath ) ;
114+ const rootPackageName = rootPackage . name ;
115+
116+ const requestedSkips = getSkippedPackageNames ( args ) ;
117+ const rootAliases = new Set ( [ 'root' , 'main' , rootPackageName ] ) ;
118+ const skipRootPackage = Array . from ( requestedSkips ) . some ( name => rootAliases . has ( name ) ) ;
119+
120+ const implementationPackages = packages . filter ( pkg => ! requestedSkips . has ( pkg . name ) ) ;
121+ const skippedImplementationPackages = packages . filter ( pkg => requestedSkips . has ( pkg . name ) ) ;
122+
123+ const knownPackageNames = new Set ( [ rootPackageName , 'root' , 'main' , ...packages . map ( pkg => pkg . name ) ] ) ;
124+ const unknownSkippedPackages = Array . from ( requestedSkips ) . filter ( name => ! knownPackageNames . has ( name ) ) ;
125+
76126 logInfo ( `Release version: ${ version } ` ) ;
77- logInfo ( `Packages to publish: ${ packages . length + 1 } ` ) ;
127+ logInfo ( `Packages to publish: ${ implementationPackages . length + ( skipRootPackage ? 0 : 1 ) } ` ) ;
78128
79- // Step 2: Get commit message for main package
80- logStep ( '2' , 'Getting commit message for main package...' ) ;
81- const defaultMainCommit = `Release v${ version } ` ;
82- const mainCommitMessage = await question ( `Commit message for main package (press Enter for "${ defaultMainCommit } "): ` ) ;
83- const finalMainCommit = mainCommitMessage . trim ( ) || defaultMainCommit ;
84- logInfo ( `Main package commit: "${ finalMainCommit } "` ) ;
129+ if ( skipRootPackage || skippedImplementationPackages . length > 0 ) {
130+ logWarning ( 'Some packages were skipped by CLI options' ) ;
131+ if ( skipRootPackage ) {
132+ logInfo ( `Skipped root package: ${ rootPackageName } ` ) ;
133+ }
134+ if ( skippedImplementationPackages . length > 0 ) {
135+ logInfo ( `Skipped implementations: ${ skippedImplementationPackages . map ( pkg => pkg . name ) . join ( ', ' ) } ` ) ;
136+ }
137+ }
85138
86- // Step 3: Test and build main package
87- logStep ( '3' , 'Testing main package...' ) ;
88- const testResult = testPackage ( rootDir , false ) ;
89- if ( testResult . success === false ) {
90- logError ( 'Tests failed for main package!' ) ;
91- console . log ( testResult . error ) ;
92- process . exit ( 1 ) ;
139+ if ( unknownSkippedPackages . length > 0 ) {
140+ logWarning ( `Unknown package names in skip list: ${ unknownSkippedPackages . join ( ', ' ) } ` ) ;
93141 }
94- logSuccess ( 'Tests passed' ) ;
95142
96- logStep ( '4' , 'Building main package...' ) ;
97- buildPackage ( rootDir , false ) ;
98- logSuccess ( 'Build completed' ) ;
143+ // Step 2: Get commit message for main package
144+ let finalMainCommit ;
145+ if ( ! skipRootPackage ) {
146+ logStep ( '2' , 'Getting commit message for main package...' ) ;
147+ const defaultMainCommit = `Release v${ version } ` ;
148+ const mainCommitMessage = await question ( `Commit message for main package (press Enter for "${ defaultMainCommit } "): ` ) ;
149+ finalMainCommit = mainCommitMessage . trim ( ) || defaultMainCommit ;
150+ logInfo ( `Main package commit: "${ finalMainCommit } "` ) ;
151+ } else {
152+ logStep ( '2' , 'Skipping main package commit message...' ) ;
153+ logInfo ( 'Main package was skipped by CLI options' ) ;
154+ }
99155
100- // Step 5: Commit main package
101- logStep ( '5' , 'Committing main package...' ) ;
102- stageFiles ( [ '.' ] , false ) ; // Stage all changes
103- commit ( finalMainCommit , false ) ;
104- logSuccess ( 'Main package committed' ) ;
156+ // Step 3: Test and build main package
157+ if ( ! skipRootPackage ) {
158+ logStep ( '3' , 'Testing main package...' ) ;
159+ const testResult = testPackage ( rootDir , false ) ;
160+ if ( testResult . success === false ) {
161+ logError ( 'Tests failed for main package!' ) ;
162+ console . log ( testResult . error ) ;
163+ process . exit ( 1 ) ;
164+ }
165+ logSuccess ( 'Tests passed' ) ;
105166
106- // Step 6: Publish main package
107- logStep ( '6' , 'Publishing main package...' ) ;
108- logWarning ( 'Publishing main package - this will open a browser for 2FA authorization' ) ;
109- logInfo ( 'After authorizing in the browser, you have 5 minutes to publish all packages' ) ;
110- publishPackage ( rootDir , false ) ;
111- logSuccess ( `Published vintasend@${ version } to npm` ) ;
167+ logStep ( '4' , 'Building main package...' ) ;
168+ buildPackage ( rootDir , false ) ;
169+ logSuccess ( 'Build completed' ) ;
112170
113- logWarning ( 'Please confirm you have authorized npm publish in your browser' ) ;
114- await question ( 'Press Enter after authorizing in the browser: ' ) ;
115- logSuccess ( 'Authorization confirmed - proceeding with implementation publishing' ) ;
171+ // Step 5: Commit main package
172+ logStep ( '5' , 'Committing main package...' ) ;
173+ stageFiles ( [ '.' ] , false ) ; // Stage all changes
174+ commit ( finalMainCommit , false ) ;
175+ logSuccess ( 'Main package committed' ) ;
176+
177+ // Step 6: Publish main package
178+ logStep ( '6' , 'Publishing main package...' ) ;
179+ logWarning ( 'Publishing main package - this will open a browser for 2FA authorization' ) ;
180+ logInfo ( 'After authorizing in the browser, you have 5 minutes to publish all packages' ) ;
181+ publishPackage ( rootDir , false ) ;
182+ logSuccess ( `Published ${ rootPackageName } @${ version } to npm` ) ;
183+
184+ logWarning ( 'Please confirm you have authorized npm publish in your browser' ) ;
185+ await question ( 'Press Enter after authorizing in the browser: ' ) ;
186+ logSuccess ( 'Authorization confirmed - proceeding with implementation publishing' ) ;
187+ } else {
188+ logStep ( '3' , 'Skipping main package test/build/commit/publish...' ) ;
189+ logWarning ( 'Root package publishing was skipped. Ensure npm auth is valid before publishing implementations.' ) ;
190+ }
116191
117192 // Step 7: For each implementation, get commit message, test, build, commit, and publish
118- logStep ( '7' , `Publishing ${ packages . length } implementation packages...` ) ;
193+ logStep ( '7' , `Publishing ${ implementationPackages . length } implementation packages...` ) ;
194+
195+ let publishedImplementations = 0 ;
119196
120- for ( let i = 0 ; i < packages . length ; i ++ ) {
121- const pkg = packages [ i ] ;
197+ if ( implementationPackages . length === 0 ) {
198+ logWarning ( 'No implementation packages left to publish after applying skip list' ) ;
199+ }
200+
201+ for ( let i = 0 ; i < implementationPackages . length ; i ++ ) {
202+ const pkg = implementationPackages [ i ] ;
122203 const pkgNum = i + 1 ;
123204
124205 log ( `\n${ '─' . repeat ( 60 ) } ` , 'cyan' ) ;
125- log ( `Package ${ pkgNum } /${ packages . length } : ${ pkg . name } ` , 'bright' ) ;
206+ log ( `Package ${ pkgNum } /${ implementationPackages . length } : ${ pkg . name } ` , 'bright' ) ;
126207 log ( '─' . repeat ( 60 ) , 'cyan' ) ;
127208
128209 // Get commit message for this implementation
@@ -167,6 +248,7 @@ async function main() {
167248 try {
168249 publishPackage ( pkg . dir , false ) ;
169250 logSuccess ( `Published ${ pkg . name } @${ version } ` ) ;
251+ publishedImplementations += 1 ;
170252 } catch ( error ) {
171253 logError ( `Failed to publish ${ pkg . name } : ${ error . message } ` ) ;
172254 }
@@ -182,7 +264,11 @@ async function main() {
182264 log ( '✓ RELEASE COMPLETED SUCCESSFULLY!' , 'green' ) ;
183265 log ( '=' . repeat ( 50 ) , 'green' ) ;
184266 console . log ( `\nReleased version: ${ version } ` ) ;
185- console . log ( `Packages published: ${ packages . length + 1 } ` ) ;
267+ console . log ( `Packages published: ${ publishedImplementations + ( skipRootPackage ? 0 : 1 ) } ` ) ;
268+ if ( skipRootPackage || skippedImplementationPackages . length > 0 ) {
269+ const skippedCount = skippedImplementationPackages . length + ( skipRootPackage ? 1 : 0 ) ;
270+ console . log ( `Packages skipped: ${ skippedCount } ` ) ;
271+ }
186272 console . log ( '\nNext steps:' ) ;
187273 console . log ( ' 1. Review the commits: git log' ) ;
188274 console . log ( ' 2. Push to remote: git push' ) ;
0 commit comments