Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

fix(gatsby): close parcel cache db before clearing cache and retrying #36377

Merged
merged 4 commits into from
Aug 18, 2022
Merged
Show file tree
Hide file tree
Changes from 1 commit
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
1 change: 1 addition & 0 deletions packages/gatsby/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -30,6 +30,7 @@
"@graphql-tools/load": "^7.5.10",
"@jridgewell/trace-mapping": "^0.3.13",
"@nodelib/fs.walk": "^1.2.8",
"@parcel/cache": "2.6.2",
"@parcel/core": "2.6.2",
"@pmmmwh/react-refresh-webpack-plugin": "^0.4.3",
"@types/http-proxy": "^1.17.7",
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,7 @@

exports[`gatsby file compilation constructBundler should construct Parcel relative to passed directory 1`] = `
Object {
"cache": undefined,
"cacheDir": "<PROJECT_ROOT>/packages/gatsby/src/utils/parcel/__tests__/fixtures/js/.cache/.parcel-cache",
"defaultConfig": "<PROJECT_ROOT>/packages/gatsby-parcel-config/lib/index.json",
"entries": Array [
Expand Down
31 changes: 27 additions & 4 deletions packages/gatsby/src/utils/parcel/compile-gatsby-files.ts
Original file line number Diff line number Diff line change
@@ -1,4 +1,5 @@
import { Parcel } from "@parcel/core"
import { LMDBCache, Cache } from "@parcel/cache"
import path from "path"
import type { Diagnostic } from "@parcel/diagnostic"
import reporter from "gatsby-cli/lib/reporter"
Expand Down Expand Up @@ -27,14 +28,15 @@ function exponentialBackoff(retry: number): Promise<void> {
* Construct Parcel with config.
* @see {@link https://parceljs.org/features/targets/}
*/
export function constructParcel(siteRoot: string): Parcel {
export function constructParcel(siteRoot: string, cache?: Cache): Parcel {
return new Parcel({
entries: [
`${siteRoot}/${gatsbyFileRegex}`,
`${siteRoot}/plugins/**/${gatsbyFileRegex}`,
],
defaultConfig: require.resolve(`gatsby-parcel-config`),
mode: `production`,
cache,
targets: {
root: {
outputFormat: `commonjs`,
Expand Down Expand Up @@ -100,8 +102,22 @@ export async function compileGatsbyFiles(

await exponentialBackoff(retry)

const parcel = constructParcel(siteRoot)
// for whatever reason TS things LMDBCache is some browser Cache and not actually Parcel's Cache
pieh marked this conversation as resolved.
Show resolved Hide resolved
// so we force type it to Parcel's Cache
const cache = new LMDBCache(getCacheDir(siteRoot)) as any as Cache
pieh marked this conversation as resolved.
Show resolved Hide resolved
const parcel = constructParcel(siteRoot, cache)
const { bundleGraph } = await parcel.run()
let cacheClosePromise = Promise.resolve()
try {
// @ts-ignore store is public field on LMDBCache class, but public interface for Cache
// doesn't have it. There doesn't seem to be proper public API for this, so we have to
// resort to reaching into internals. Just in case this is wrapped in try/catch if
// parcel changes internals in future (closing cache is only needed when retrying
// so the if the change happens we shouldn't fail on happy builds)
cacheClosePromise = cache.store.close()
} catch (e) {
reporter.verbose(`Failed to close parcel cache\n${e.toString()}`)
}

await exponentialBackoff(retry)

Expand Down Expand Up @@ -138,8 +154,15 @@ export async function compileGatsbyFiles(
)
}

// sometimes parcel cache gets in weird state
await remove(getCacheDir(siteRoot))
// sometimes parcel cache gets in weird state and we need to clear the cache
await cacheClosePromise

try {
await remove(getCacheDir(siteRoot))
} catch {
// in windows we might get "EBUSY" errors if LMDB failed to close, so this try/catch is
// to prevent EBUSY errors from potentially hiding real import errors
}

await compileGatsbyFiles(siteRoot, retry + 1)
return
Expand Down