@@ -5,7 +5,7 @@ import { CreateTestRequestDto } from './dto/create-test-request.dto';
55import { IgnoreAreaDto } from './dto/ignore-area.dto' ;
66import { StaticService } from '../shared/static/static.service' ;
77import { PrismaService } from '../prisma/prisma.service' ;
8- import { TestRun , TestStatus , TestVariation } from '@prisma/client' ;
8+ import { Baseline , TestRun , TestStatus , TestVariation } from '@prisma/client' ;
99import { DiffResult } from './diffResult' ;
1010import { EventsGateway } from '../shared/events/events.gateway' ;
1111import { CommentDto } from '../shared/dto/comment.dto' ;
@@ -233,7 +233,8 @@ export class TestRunsService {
233233
234234 let testRunWithResult = await this . saveDiffResult ( testRun . id , diffResult ) ;
235235
236- testRunWithResult = await this . tryAutoApproveBasedOnHistory ( testVariation , testRunWithResult , image , ignoreAreas ) ;
236+ testRunWithResult = await this . tryAutoApproveByPastBaselines ( testVariation , testRunWithResult , ignoreAreas ) ;
237+ testRunWithResult = await this . tryAutoApproveByNewBaselines ( testVariation , testRunWithResult , ignoreAreas ) ;
237238
238239 this . eventsGateway . testRunCreated ( testRunWithResult ) ;
239240 return testRunWithResult ;
@@ -334,69 +335,86 @@ export class TestRunsService {
334335 return image . data ;
335336 }
336337
337- private async tryAutoApproveBasedOnHistory (
338+ /**
339+ * Reason: not rebased code from feature branch is compared agains new main branch baseline thus diff is expected
340+ * Tries to find past baseline in main branch and autoApprove in case matched
341+ * @param testVariation
342+ * @param testRun
343+ * @param ignoreAreas
344+ */
345+ private async tryAutoApproveByPastBaselines (
338346 testVariation : TestVariation ,
339347 testRun : TestRun ,
340- image : PNG ,
341348 ignoreAreas : IgnoreAreaDto [ ]
342349 ) : Promise < TestRun > {
343- if ( process . env . AUTO_APPROVE_BASED_ON_HISTORY && testRun . status !== TestStatus . ok ) {
344- this . logger . log ( `Try auto approve testRun: ${ testRun . id } ` ) ;
345-
346- const alreadyApprovedTestRuns : TestRun [ ] = await this . prismaService . testRun . findMany ( {
347- where : {
348- ...getTestVariationUniqueData ( testVariation ) ,
349- baselineName : testVariation . baselineName ,
350- status : TestStatus . approved ,
351- } ,
352- } ) ;
350+ if (
351+ ! process . env . AUTO_APPROVE_BASED_ON_HISTORY ||
352+ testRun . status === TestStatus . ok ||
353+ testRun . branchName === testRun . baselineBranchName
354+ ) {
355+ return testRun ;
356+ }
353357
354- let autoApproved = false ;
355- for ( const approvedTestRun of alreadyApprovedTestRuns ) {
356- this . logger . log (
357- `Found already approved baseline for testRun: ${ testRun . id }
358- testVariation: ${ approvedTestRun . testVariationId }
359- branch: ${ approvedTestRun . branchName }
360- testRun: ${ approvedTestRun . id }
361- build: ${ approvedTestRun . buildId } `
362- ) ;
358+ this . logger . log ( `Try AutoApproveByPastBaselines testRun: ${ testRun . id } ` ) ;
359+ const testVariationHistory = await this . testVariationService . getDetails ( testVariation . id ) ;
360+ // skip first baseline as it was used by default in general flow
361+ for ( const baseline of testVariationHistory . baselines . slice ( 1 ) ) {
362+ if ( this . shouldAutoApprove ( baseline , testRun , ignoreAreas ) ) {
363+ return this . approve ( testRun . id , false , true ) ;
364+ }
365+ }
363366
364- const approvedTestVariation = await this . prismaService . testVariation . findUnique ( {
365- where : {
366- id : approvedTestRun . testVariationId ,
367- } ,
368- } ) ;
367+ return testRun ;
368+ }
369+
370+ /**
371+ * Reason: branch got another one merged thus diff is expected
372+ * Tries to find latest baseline in test variation
373+ * that has already approved test agains the same baseline image
374+ * and autoApprove in case matched
375+ * @param testVariation
376+ * @param testRun
377+ * @param image
378+ * @param ignoreAreas
379+ */
380+ private async tryAutoApproveByNewBaselines (
381+ testVariation : TestVariation ,
382+ testRun : TestRun ,
383+ ignoreAreas : IgnoreAreaDto [ ]
384+ ) : Promise < TestRun > {
385+ if ( ! process . env . AUTO_APPROVE_BASED_ON_HISTORY || testRun . status === TestStatus . ok ) {
386+ return testRun ;
387+ }
388+ this . logger . log ( `Try AutoApproveByNewBaselines testRun: ${ testRun . id } ` ) ;
369389
370- const approvedBaseline = this . staticService . getImage ( approvedTestVariation . baselineName ) ;
371- const diffResult = this . getDiff ( approvedBaseline , image , testRun . diffTollerancePercent , ignoreAreas ) ;
390+ const alreadyApprovedTestRuns : TestRun [ ] = await this . prismaService . testRun . findMany ( {
391+ where : {
392+ ...getTestVariationUniqueData ( testVariation ) ,
393+ baselineName : testVariation . baselineName ,
394+ status : TestStatus . approved ,
395+ } ,
396+ } ) ;
372397
373- if ( diffResult . status === TestStatus . ok ) {
374- autoApproved = true ;
375- const baseline = await this . prismaService . baseline . findFirst ( {
376- where : {
377- testVariationId : approvedTestVariation . id ,
378- baselineName : approvedTestVariation . baselineName ,
379- } ,
380- include : {
381- testRun : true ,
382- } ,
383- } ) ;
384- this . logger . log (
385- `Found reason to auto approve testRun: ${ testRun . id }
386- testVariation: ${ baseline . testVariationId }
387- baseline: ${ baseline . id }
388- branch: ${ approvedTestVariation . branchName }
389- testRun: ${ baseline . testRunId }
390- build: ${ baseline . testRun . buildId } `
391- ) ;
392- }
393- }
398+ for ( const approvedTestRun of alreadyApprovedTestRuns ) {
399+ const approvedTestVariation = await this . testVariationService . getDetails ( approvedTestRun . testVariationId ) ;
400+ const baseline = approvedTestVariation . baselines . shift ( ) ;
394401
395- if ( autoApproved ) {
402+ if ( this . shouldAutoApprove ( baseline , testRun , ignoreAreas ) ) {
396403 return this . approve ( testRun . id , false , true ) ;
397404 }
398- this . logger . log ( `Cannot auto approve testRun: ${ testRun . id } ` ) ;
399405 }
406+
400407 return testRun ;
401408 }
409+
410+ private shouldAutoApprove ( baseline : Baseline , testRun : TestRun , ignoreAreas : Array < IgnoreAreaDto > ) : boolean {
411+ const approvedImage = this . staticService . getImage ( baseline . baselineName ) ;
412+ const image = this . staticService . getImage ( testRun . imageName ) ;
413+ const diffResult = this . getDiff ( approvedImage , image , testRun . diffTollerancePercent , ignoreAreas ) ;
414+
415+ if ( diffResult . status === TestStatus . ok ) {
416+ this . logger . log ( `TestRun ${ testRun . id } could be auto approved based on Baseline ${ baseline . id } ` ) ;
417+ return true ;
418+ }
419+ }
402420}
0 commit comments