Skip to content

Commit

Permalink
chore: add clearCache
Browse files Browse the repository at this point in the history
  • Loading branch information
sheremet-va committed Jul 2, 2022
1 parent 01a23ce commit 795518c
Show file tree
Hide file tree
Showing 13 changed files with 123 additions and 24 deletions.
4 changes: 2 additions & 2 deletions docs/config/index.md
Expand Up @@ -567,11 +567,11 @@ Test above this limit will be queued to run when available slot appears.

### cache

- **Type**: `false | { path? }`
- **Type**: `false | { dir? }`

Options to configure Vitest cache policy. At the moment Vitest stores cache for test results to run the longer and failed tests first.

#### cache.path
#### cache.dir

- **Type**: `string`
- **Default**: `node_modules/.vitest`
Expand Down
4 changes: 4 additions & 0 deletions docs/guide/cli.md
Expand Up @@ -36,6 +36,10 @@ Useful to run with [`lint-staged`](https://github.com/okonet/lint-staged) or wit
vitest related /src/index.ts /src/hello-world.js
```

### `vitest clearCache`

Clears cache folder.

## Options

| Options | |
Expand Down
36 changes: 36 additions & 0 deletions packages/vitest/src/node/cache/index.ts
@@ -0,0 +1,36 @@
import fs from 'fs'
import { findUp } from 'find-up'
import { resolve } from 'pathe'
import { loadConfigFromFile } from 'vite'
import { configFiles } from '../../constants'
import type { CliOptions } from '../cli-api'
import { slash } from '../../utils'

export class VitestCache {
static resolveCacheDir(root: string, dir: string | undefined) {
return resolve(root, slash(dir || 'node_modules/.vitest'))
}

static async clearCache(options: CliOptions) {
const root = resolve(options.root || process.cwd())

const configPath = options.config
? resolve(root, options.config)
: await findUp(configFiles, { cwd: root } as any)

const config = await loadConfigFromFile({ command: 'serve', mode: 'test' }, configPath)

if (!config)
throw new Error(`[vitest] Not able to load config from ${configPath}`)

const cache = config.config.test?.cache

if (!cache)
throw new Error('[vitest] Cache is disabled')

const cachePath = VitestCache.resolveCacheDir(root, cache.dir)

if (fs.existsSync(cachePath))
fs.rmSync(cachePath, { recursive: true, force: true })
}
}
@@ -1,7 +1,7 @@
import fs from 'fs'
import { dirname, resolve } from 'pathe'
import type { File, ResolvedConfig } from '../types'
import { version } from '../../package.json'
import type { File, ResolvedConfig } from '../../types'
import { version } from '../../../package.json'

interface SuiteResultCache {
failed: boolean
Expand All @@ -10,23 +10,23 @@ interface SuiteResultCache {

export class ResultsCache {
private cache = new Map<string, SuiteResultCache>()
public config!: ResolvedConfig['cache']
private cachePath: string | null = null

setConfig(config: ResolvedConfig['cache']) {
this.config = config
if (config)
this.cachePath = resolve(config.dir, 'results.json')
}

getResults(id: string) {
return this.cache.get(id)
}

async readFromCache() {
if (this.config === false)
if (!this.cachePath)
return

const resultsCachePath = resolve(this.config.path, 'results.json')
if (fs.existsSync(resultsCachePath)) {
const resultsCache = await fs.promises.readFile(resultsCachePath, 'utf8')
if (fs.existsSync(this.cachePath)) {
const resultsCache = await fs.promises.readFile(this.cachePath, 'utf8')
this.cache = new Map(JSON.parse(resultsCache).results)
}
}
Expand All @@ -49,18 +49,17 @@ export class ResultsCache {
}

async writeToCache() {
if (this.config === false)
if (!this.cachePath)
return

const resultsCachePath = resolve(this.config.path, 'results.json')
const resultsCache = Array.from(this.cache.entries())

const cacheDirname = dirname(resultsCachePath)
const cacheDirname = dirname(this.cachePath)

if (!fs.existsSync(cacheDirname))
await fs.promises.mkdir(cacheDirname, { recursive: true })

await fs.promises.writeFile(resultsCachePath, JSON.stringify({
await fs.promises.writeFile(this.cachePath, JSON.stringify({
version,
results: resultsCache,
}))
Expand Down
4 changes: 4 additions & 0 deletions packages/vitest/src/node/cli.ts
@@ -1,6 +1,7 @@
import cac from 'cac'
import c from 'picocolors'
import { version } from '../../package.json'
import { VitestCache } from './cache'
import type { CliOptions } from './cli-api'
import { startVitest } from './cli-api'
import { divider } from './reporters/renderers/utils'
Expand Down Expand Up @@ -57,6 +58,9 @@ cli
.command('[...filters]')
.action(start)

cli.command('clearCache')
.action(VitestCache.clearCache)

cli.parse()

async function runRelated(relatedFiles: string[] | string, argv: CliOptions) {
Expand Down
11 changes: 5 additions & 6 deletions packages/vitest/src/node/config.ts
Expand Up @@ -7,7 +7,8 @@ import type { ApiConfig, ResolvedConfig, UserConfig } from '../types'
import { defaultPort } from '../constants'
import { configDefaults } from '../defaults'
import { resolveC8Options } from '../integrations/coverage'
import { slash, toArray } from '../utils'
import { toArray } from '../utils'
import { VitestCache } from './cache'

const extraInlineDeps = [
/^(?!.*(?:node_modules)).*\.mjs$/,
Expand Down Expand Up @@ -179,11 +180,9 @@ export function resolveConfig(
if (typeof resolved.css === 'object')
resolved.css.include ??= [/\.module\./]

resolved.cache ??= { path: '' }
if (resolved.cache) {
const path = slash(resolved.cache.path || 'node_modules/.vitest')
resolved.cache.path = resolve(resolved.root, path)
}
resolved.cache ??= { dir: '' }
if (resolved.cache)
resolved.cache.dir = VitestCache.resolveCacheDir(resolved.root, resolved.cache.dir)

return resolved
}
2 changes: 1 addition & 1 deletion packages/vitest/src/node/state.ts
@@ -1,5 +1,5 @@
import type { ErrorWithDiff, File, Task, TaskResultPack, UserConsoleLog } from '../types'
import { ResultsCache } from './cache'
import { ResultsCache } from './cache/results'

export class StateManager {
filesMap = new Map<string, File>()
Expand Down
6 changes: 3 additions & 3 deletions packages/vitest/src/types/config.ts
Expand Up @@ -364,10 +364,10 @@ export interface InlineConfig {

/**
* Options for configuring cache policy.
* @default { path: 'node_modules/.vitest' }
* @default { dir: 'node_modules/.vitest' }
*/
cache?: false | {
path?: string
dir?: string
}
}

Expand Down Expand Up @@ -437,6 +437,6 @@ export interface ResolvedConfig extends Omit<Required<UserConfig>, 'config' | 'f
}

cache: {
path: string
dir: string
} | false
}
1 change: 1 addition & 0 deletions test/cache/.gitignore
@@ -0,0 +1 @@
cache/*
11 changes: 11 additions & 0 deletions test/cache/package.json
@@ -0,0 +1,11 @@
{
"name": "@vitest/test-cache",
"private": true,
"scripts": {
"test": "vitest",
"coverage": "vitest run --coverage"
},
"devDependencies": {
"vitest": "workspace:*"
}
}
26 changes: 26 additions & 0 deletions test/cache/test/clear-cache.test.ts
@@ -0,0 +1,26 @@
import fs, { promises as fsp } from 'fs'
import { resolve } from 'pathe'
import { describe, expect, test } from 'vitest'
import { VitestCache } from '../../../packages/vitest/src/node/cache/index'

const root = resolve(__dirname, '..')

const pathBase = resolve(root, 'cache/.vitest-base')
const pathCustom = resolve(root, 'cache/.vitest-custom')

describe('vitest cache', async () => {
await fsp.mkdir(pathBase, { recursive: true })
await fsp.mkdir(pathCustom, { recursive: true })

test('clears cache without specifying config path', async () => {
await VitestCache.clearCache({})

expect(fs.existsSync(pathBase)).toBe(false)
})

test('clears cache with specified config path', async () => {
await VitestCache.clearCache({ config: 'vitest-custom.config.ts' })

expect(fs.existsSync(pathCustom)).toBe(false)
})
})
9 changes: 9 additions & 0 deletions test/cache/vitest-custom.config.ts
@@ -0,0 +1,9 @@
import { defineConfig } from 'vite'

export default defineConfig({
test: {
cache: {
dir: 'cache/.vitest-custom',
},
},
})
10 changes: 10 additions & 0 deletions test/cache/vitest.config.ts
@@ -0,0 +1,10 @@
import { defineConfig } from 'vite'

export default defineConfig({
test: {
threads: false,
cache: {
dir: 'cache/.vitest-base',
},
},
})

0 comments on commit 795518c

Please sign in to comment.