7
7
8
8
import * as path from 'path' ;
9
9
import * as os from 'os' ;
10
- import { Readable } from 'stream' ;
11
10
import * as glob from 'glob' ;
12
11
import { pwd } from 'shelljs' ;
13
12
import { AnyJson , ensureString , getString } from '@salesforce/ts-types' ;
14
13
import { UX } from '@salesforce/command' ;
15
14
import { exec , ShellString } from 'shelljs' ;
16
15
import { fs , Logger , SfdxError } from '@salesforce/core' ;
17
16
import { AsyncOptionalCreatable , Env , isEmpty , sleep } from '@salesforce/kit' ;
18
- import { Nullable , isString } from '@salesforce/ts-types' ;
17
+ import { isString } from '@salesforce/ts-types' ;
19
18
import * as chalk from 'chalk' ;
20
- import * as conventionalCommitsParser from 'conventional-commits-parser' ;
21
- import * as conventionalChangelogPresetLoader from 'conventional-changelog-preset-loader' ;
22
19
import { api as packAndSignApi , SigningResponse } from './codeSigning/packAndSign' ;
23
20
import { upload } from './codeSigning/upload' ;
24
21
import { Package , VersionValidation } from './package' ;
25
22
import { Registry } from './registry' ;
23
+ import { inspectCommits } from './inspectCommits' ;
26
24
27
25
export type LernaJson = {
28
26
packages ?: string [ ] ;
@@ -49,12 +47,6 @@ interface VersionsByPackage {
49
47
} ;
50
48
}
51
49
52
- interface Commit {
53
- type : Nullable < string > ;
54
- header : Nullable < string > ;
55
- body : Nullable < string > ;
56
- }
57
-
58
50
type PollFunction = ( ) => boolean ;
59
51
60
52
export async function isMonoRepo ( ) : Promise < boolean > {
@@ -235,46 +227,8 @@ abstract class Repository extends AsyncOptionalCreatable<RepositoryOptions> {
235
227
* the commits to see if any of them indicate that a new release should be published.
236
228
*/
237
229
protected async isReleasable ( pkg : Package , lerna = false ) : Promise < boolean > {
238
- // Return true if the version bump is hardcoded in the package.json
239
- // In this scenario, we want to publish regardless of the commit types
240
- if ( pkg . nextVersionIsHardcoded ( ) ) return true ;
241
-
242
- const skippableCommitTypes = [ 'chore' , 'style' , 'docs' , 'ci' , 'test' ] ;
243
-
244
- // find the latest git tag so that we can get all the commits that have happened since
245
- const tags = this . execCommand ( 'git fetch --tags && git tag' , true ) . stdout . split ( os . EOL ) ;
246
- const latestTag = lerna
247
- ? tags . find ( ( tag ) => tag . includes ( `${ pkg . name } @${ pkg . npmPackage . version } ` ) ) || ''
248
- : tags . find ( ( tag ) => tag . includes ( pkg . npmPackage . version ) ) ;
249
-
250
- // import the default commit parser configuration
251
- const defaultConfigPath = require . resolve ( 'conventional-changelog-conventionalcommits' ) ;
252
- const configuration = await conventionalChangelogPresetLoader ( { name : defaultConfigPath } ) ;
253
-
254
- const commits : Commit [ ] = await new Promise ( ( resolve ) => {
255
- const DELIMITER = 'SPLIT' ;
256
- const gitLogCommand = lerna
257
- ? `git log --format=%B%n-hash-%n%H%n${ DELIMITER } ${ latestTag } ..HEAD --no-merges -- ${ pkg . location } `
258
- : `git log --format=%B%n-hash-%n%H%n${ DELIMITER } ${ latestTag } ..HEAD --no-merges` ;
259
- const gitLog = this . execCommand ( gitLogCommand , true )
260
- . stdout . split ( `${ DELIMITER } ${ os . EOL } ` )
261
- . filter ( ( c ) => ! ! c ) ;
262
- const readable = Readable . from ( gitLog ) ;
263
- // eslint-disable-next-line @typescript-eslint/ban-ts-comment
264
- // @ts -ignore because the type exported from conventionalCommitsParser is wrong
265
- const parser = readable . pipe ( conventionalCommitsParser ( configuration . parserOpts ) ) ;
266
- const allCommits : Commit [ ] = [ ] ;
267
- parser . on ( 'data' , ( commit : Commit ) => allCommits . push ( commit ) ) ;
268
- parser . on ( 'finish' , ( ) => resolve ( allCommits ) ) ;
269
- } ) ;
270
-
271
- const commitsThatWarrantRelease = commits . filter ( ( commit ) => {
272
- const headerIndicatesMajorChange = ! ! commit . header && commit . header . includes ( '!' ) ;
273
- const bodyIndicatesMajorChange = ! ! commit . body && commit . body . includes ( 'BREAKING' ) ;
274
- const typeIsSkippable = skippableCommitTypes . includes ( commit . type ) ;
275
- return ! typeIsSkippable || bodyIndicatesMajorChange || headerIndicatesMajorChange ;
276
- } ) ;
277
- return commitsThatWarrantRelease . length > 0 ;
230
+ const commitInspection = await inspectCommits ( pkg , lerna ) ;
231
+ return commitInspection . shouldRelease ;
278
232
}
279
233
280
234
public abstract getSuccessMessage ( ) : string ;
@@ -298,6 +252,28 @@ export class LernaRepo extends Repository {
298
252
super ( options ) ;
299
253
}
300
254
255
+ public static async getPackages ( ) : Promise < Package [ ] > {
256
+ const pkgPaths = await LernaRepo . getPackagePaths ( ) ;
257
+ const packages : Package [ ] = [ ] ;
258
+ for ( const pkgPath of pkgPaths ) {
259
+ packages . push ( await Package . create ( pkgPath ) ) ;
260
+ }
261
+ return packages ;
262
+ }
263
+
264
+ public static async getPackagePaths ( ) : Promise < string [ ] > {
265
+ const workingDir = pwd ( ) . stdout ;
266
+ const lernaJson = ( await fs . readJson ( 'lerna.json' ) ) as LernaJson ;
267
+ // https://github.com/lerna/lerna#lernajson
268
+ // "By default, lerna initializes the packages list as ["packages/*"]"
269
+ const packageGlobs = lernaJson . packages || [ '*' ] ;
270
+ const packages = packageGlobs
271
+ . map ( ( pGlob ) => glob . sync ( pGlob ) )
272
+ . reduce ( ( x , y ) => x . concat ( y ) , [ ] )
273
+ . map ( ( pkg ) => path . join ( workingDir , pkg ) ) ;
274
+ return packages ;
275
+ }
276
+
301
277
public validate ( ) : VersionValidation [ ] {
302
278
return this . packages . map ( ( pkg ) => pkg . validateNextVersion ( ) ) ;
303
279
}
@@ -366,18 +342,9 @@ export class LernaRepo extends Repository {
366
342
return `${ header } ${ os . EOL } ${ successes } ` ;
367
343
}
368
344
369
- public async getPackages ( ) : Promise < Package [ ] > {
370
- const pkgPaths = await this . getPackagePaths ( ) ;
371
- const packages : Package [ ] = [ ] ;
372
- for ( const pkgPath of pkgPaths ) {
373
- packages . push ( await Package . create ( pkgPath ) ) ;
374
- }
375
- return packages ;
376
- }
377
-
378
345
protected async init ( ) : Promise < void > {
379
346
this . logger = await Logger . child ( this . constructor . name ) ;
380
- const pkgPaths = await this . getPackagePaths ( ) ;
347
+ const pkgPaths = await LernaRepo . getPackagePaths ( ) ;
381
348
const nextVersions = this . determineNextVersionByPackage ( ) ;
382
349
if ( ! isEmpty ( nextVersions ) ) {
383
350
for ( const pkgPath of pkgPaths ) {
@@ -392,19 +359,6 @@ export class LernaRepo extends Repository {
392
359
}
393
360
}
394
361
395
- private async getPackagePaths ( ) : Promise < string [ ] > {
396
- const workingDir = pwd ( ) . stdout ;
397
- const lernaJson = ( await fs . readJson ( 'lerna.json' ) ) as LernaJson ;
398
- // https://github.com/lerna/lerna#lernajson
399
- // "By default, lerna initializes the packages list as ["packages/*"]"
400
- const packageGlobs = lernaJson . packages || [ 'packages/*' ] ;
401
- const packages = packageGlobs
402
- . map ( ( pGlob ) => glob . sync ( pGlob ) )
403
- . reduce ( ( x , y ) => x . concat ( y ) , [ ] )
404
- . map ( ( pkg ) => path . join ( workingDir , pkg ) ) ;
405
- return packages ;
406
- }
407
-
408
362
private determineNextVersionByPackage ( ) : VersionsByPackage {
409
363
const currentVersionRegex = / (?< = : \s ) ( [ 0 - 9 ] { 1 , } \. | .) { 2 , } (? = \s = > ) / gi;
410
364
const nextVersionsRegex = / (?< = = > \s ) ( [ 0 - 9 ] { 1 , } \. | .) { 2 , } / gi;
@@ -502,9 +456,8 @@ export class SinglePackageRepo extends Repository {
502
456
}
503
457
504
458
protected async init ( ) : Promise < void > {
505
- const packagePath = pwd ( ) . stdout ;
506
459
this . logger = await Logger . child ( this . constructor . name ) ;
507
- this . package = await Package . create ( packagePath ) ;
460
+ this . package = await Package . create ( ) ;
508
461
this . shouldBePublished = await this . isReleasable ( this . package ) ;
509
462
this . nextVersion = this . determineNextVersion ( ) ;
510
463
this . package . setNextVersion ( this . nextVersion ) ;
0 commit comments