All files / src index.ts

0% Statements 0/80
0% Branches 0/38
0% Functions 0/5
0% Lines 0/76

Press n or j to go to the next uncovered block, b, p or k for the previous block.

1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170                                                                                                                                                                                                                                                                                                                                                   
#!/usr/bin/env node
 
import chalk from 'chalk'
import { createCommand } from 'commander'
import execa from 'execa'
import fs from 'fs'
import { dirname, join, resolve } from 'path'
import { App } from 'rete-kit'
 
import { fixtures, getFeatures, stackNames, validate } from './commands/init'
import { validateSnapshotsUpdate, validateTestRun } from './commands/test'
import { appsCachePath, projects } from './consts'
import { log } from './ui'
 
const program = createCommand()
 
program.version(require('../package.json').version)
 
program
  .command('init')
  .description(`Initialize testing tool`)
  .option('-d --deps-alias <deps-alias>')
  .option('-n --next')
  .option('-s --stack <stack>', `Stacks to test, comma-separated (${stackNames.join(',')})`)
  .option('-sv --stack-versions <stack-version>', `Versions to test, comma-separated`)
  .action(async (options: { depsAlias: string, stack?: string, stackVersions?: string, next?: boolean }) => {
    const next = options.next || false
    const cwd = process.cwd()
    const depsAlias = options.depsAlias
      ? resolve(cwd, options.depsAlias)
      : undefined
    const stacks = options.stack
      ? options.stack.split(',')
      : stackNames
    const stackVersions = options.stackVersions
      ? options.stackVersions.split(',')
      : null
    let exitCode = 0
 
    const { error } = validate(stacks, stackVersions)
 
    Iif (error) {
      log('fail', 'FAIL')(chalk.red(error))
      process.exit(1)
    }
 
    await fs.promises.mkdir(join(cwd, appsCachePath), { recursive: true })
 
    for (const fixture of fixtures) {
      const features = getFeatures(fixture, next)
      const { folder, stack, version } = fixture
 
      Iif (!stacks.includes(stack)) continue
      Iif (stackVersions && !stackVersions.includes(String(version))) continue
 
      log('success')('Start creating', chalk.yellow(stack, `v${version}`), 'application in ', folder)
 
      try {
        process.chdir(join(cwd, appsCachePath))
        await App.createApp({
          name: folder,
          stack,
          version,
          features: features.map(f => f && f.name).filter(Boolean) as string[],
          depsAlias,
          next
        })
        await execa('npm', ['run', 'build'], { cwd: join(cwd, appsCachePath, folder) })
      } catch (err) {
        console.error(err)
        log('fail', 'FAIL')('Initialization of', folder, 'failed.')
        exitCode = 1
      }
    }
    Iif (exitCode) {
      process.exit(exitCode)
    }
  })
 
interface TestOptions {
  updateSnapshots?: boolean
  stack?: string
  stackVersions?: string
  project?: string
  grep?: string
}
 
program
  .command('test')
  .description(`Run tests for previously initialized apps`)
  .option('-u --update-snapshots', 'Update snapshots')
  .option('-g --grep <regex>', 'Match tests by name')
  .option('-s --stack <stack>', `Stacks to test, comma-separated (${stackNames.join(',')})`)
  .option('-sv --stack-versions <stack-version>', `Versions to test, comma-separated`)
  .option('-p --project <project>', `Project (${projects.map(p => p.name).join(',')})`)
  .action(async (options: TestOptions) => {
    const stacks = options.stack
      ? options.stack.split(',')
      : null
    const stackVersions = options.stackVersions
      ? options.stackVersions.split(',')
      : null
    const targetFixtures = fixtures.filter(({ stack, version }) => {
      Iif (stacks && !stacks.includes(stack)) return false
      Iif (stackVersions && !stackVersions.includes(String(version))) return false
      return true
    })
    let exitCode = 0
 
    Iif (targetFixtures.length === 0) {
      log('fail', 'FAIL')('No fixtures found for specified stacks and versions')
      process.exit(1)
    }
 
    const { error: snapshotsError } = options.updateSnapshots
      ? validateSnapshotsUpdate(targetFixtures)
      : { error: null }
 
    Iif (snapshotsError) {
      log('fail', 'FAIL')(snapshotsError)
      process.exit(1)
    }
 
    for (const fixture of targetFixtures) {
      const { folder, stack, version } = fixture
 
      try {
        log('success', 'START')('Testing in', chalk.yellow(folder), '...')
        const APP = folder
        const SERVE = App.builders[stack].getStaticPath(folder, version)
 
        const playwrightFolder = dirname(require.resolve('@playwright/test'))
 
        const { error } = await validateTestRun(APP, SERVE)
 
        Iif (error) {
          log('fail', 'FAIL')(chalk.red(error))
          exitCode = 1
          continue
        }
 
        await execa(`${playwrightFolder}/cli.js`, [
          'test',
          '--config', join(__dirname, './playwright.config.js'),
          ...options.project
            ? ['--project', options.project]
            : [],
          ...options.updateSnapshots
            ? ['--update-snapshots']
            : [],
          ...options.grep
            ? ['--grep', options.grep]
            : []
        ], { env: { APP, SERVE }, stdio: 'inherit' })
        log('success', 'DONE')('Testing for', chalk.yellow(folder), 'done')
      } catch (err) {
        console.error(err)
        log('fail', 'FAIL')('Tests in', folder, 'failed.')
        exitCode = 1
      }
    }
    Iif (exitCode) {
      process.exit(exitCode)
    }
  })
 
program.parse(process.argv)
 
export { }