perf: use hash to replace createHash (#8629)

---------

Co-authored-by: Zoltan Kochan <z@kochan.io>
This commit is contained in:
btea
2024-10-21 16:51:33 +08:00
committed by GitHub
parent 1922b4aa3f
commit 222d10ac79
23 changed files with 149 additions and 10 deletions

View File

@@ -0,0 +1,5 @@
---
"@pnpm/crypto.polyfill": major
---
Initial release.

View File

@@ -0,0 +1,10 @@
---
"@pnpm/npm-resolver": patch
"@pnpm/core": patch
"@pnpm/crypto.polyfill": patch
"@pnpm/list": patch
"@pnpm/worker": patch
"pnpm": patch
---
Use `crypto.hash`, when available, for improved performance [#8629](https://github.com/pnpm/pnpm/pull/8629).

15
crypto/polyfill/README.md Normal file
View File

@@ -0,0 +1,15 @@
# @pnpm/crypto.polyfill
> Polyfill for functions in the crypto library
[![npm version](https://img.shields.io/npm/v/@pnpm/crypto.polyfill.svg)](https://www.npmjs.com/package/@pnpm/crypto.polyfill)
## Installation
```sh
pnpm add @pnpm/crypto.polyfill
```
## License
MIT

View File

@@ -0,0 +1,38 @@
{
"name": "@pnpm/crypto.polyfill",
"version": "0.0.0",
"description": "Polyfill for functions in the crypto library",
"funding": "https://opencollective.com/pnpm",
"main": "lib/index.js",
"types": "lib/index.d.ts",
"files": [
"lib",
"!*.map"
],
"exports": {
".": "./lib/index.js"
},
"engines": {
"node": ">=18.12"
},
"scripts": {
"lint": "eslint \"src/**/*.ts\"",
"test": "pnpm run compile",
"prepublishOnly": "pnpm run compile",
"compile": "tsc --build && pnpm run lint --fix"
},
"repository": "https://github.com/pnpm/pnpm/blob/main/crypto/polyfill",
"keywords": [
"pnpm9",
"pnpm",
"crypto"
],
"license": "MIT",
"bugs": {
"url": "https://github.com/pnpm/pnpm/issues"
},
"homepage": "https://github.com/pnpm/pnpm/blob/main/crypto/polyfill#readme",
"devDependencies": {
"@pnpm/crypto.polyfill": "workspace:*"
}
}

View File

@@ -0,0 +1,10 @@
import crypto from 'crypto'
export const hash =
// @ts-expect-error -- crypto.hash is supported in Node 21.7.0+, 20.12.0+
crypto.hash ??
((
algorithm: string,
data: crypto.BinaryLike,
outputEncoding: crypto.BinaryToTextEncoding
) => crypto.createHash(algorithm).update(data).digest(outputEncoding))

View File

@@ -0,0 +1,12 @@
{
"extends": "@pnpm/tsconfig",
"compilerOptions": {
"outDir": "lib",
"rootDir": "src"
},
"include": [
"src/**/*.ts",
"../../__typings__/**/*.d.ts"
],
"references": []
}

View File

@@ -0,0 +1,8 @@
{
"extends": "./tsconfig.json",
"include": [
"src/**/*.ts",
"test/**/*.ts",
"../../__typings__/**/*.d.ts"
]
}

View File

@@ -31,6 +31,7 @@
},
"homepage": "https://github.com/pnpm/pnpm/blob/main/packages/crypto.base32-hash#readme",
"dependencies": {
"@pnpm/crypto.polyfill": "workspace:*",
"rfc4648": "catalog:"
},
"devDependencies": {

View File

@@ -1,9 +1,9 @@
import crypto from 'crypto'
import * as crypto from '@pnpm/crypto.polyfill'
import fs from 'fs'
import { base32 } from 'rfc4648'
export function createBase32Hash (str: string): string {
return base32.stringify(crypto.createHash('md5').update(str).digest()).replace(/(=+)$/, '').toLowerCase()
return base32.stringify(crypto.hash('md5', str, 'buffer')).replace(/(=+)$/, '').toLowerCase()
}
export async function createBase32HashFromFile (file: string): Promise<string> {

View File

@@ -11,6 +11,9 @@
"references": [
{
"path": "../../__utils__/prepare"
},
{
"path": "../../crypto/polyfill"
}
]
}

View File

@@ -24,6 +24,7 @@
"@pnpm/constants": "workspace:*",
"@pnpm/core-loggers": "workspace:*",
"@pnpm/crypto.base32-hash": "workspace:*",
"@pnpm/crypto.polyfill": "workspace:*",
"@pnpm/dependency-path": "workspace:*",
"@pnpm/deps.graph-sequencer": "workspace:*",
"@pnpm/error": "workspace:*",

View File

@@ -1,4 +1,3 @@
import crypto from 'crypto'
import path from 'path'
import { buildModules, type DepsStateCache, linkBinsOfDependencies } from '@pnpm/build-modules'
import { createAllowBuildFunction } from '@pnpm/builder.policy'
@@ -14,6 +13,7 @@ import {
stageLogger,
summaryLogger,
} from '@pnpm/core-loggers'
import * as crypto from '@pnpm/crypto.polyfill'
import {
calcPatchHashes,
createOverridesMapFromParsed,
@@ -746,7 +746,7 @@ Note that in CI environments, this setting is enabled by default.`,
export function createObjectChecksum (obj: Record<string, unknown>): string {
const s = JSON.stringify(sortKeys(obj, { deep: true }))
return crypto.createHash('md5').update(s).digest('hex')
return crypto.hash('md5', s, 'hex')
}
function cacheExpired (prunedAt: string, maxAgeInMinutes: number): boolean {

View File

@@ -42,6 +42,9 @@
{
"path": "../../crypto/object-hasher"
},
{
"path": "../../crypto/polyfill"
},
{
"path": "../../deps/graph-sequencer"
},

21
pnpm-lock.yaml generated
View File

@@ -1641,6 +1641,12 @@ importers:
specifier: 'catalog:'
version: 3.0.6
crypto/polyfill:
devDependencies:
'@pnpm/crypto.polyfill':
specifier: workspace:*
version: 'link:'
dedupe/check:
dependencies:
'@pnpm/dedupe.types':
@@ -3585,6 +3591,9 @@ importers:
packages/crypto.base32-hash:
dependencies:
'@pnpm/crypto.polyfill':
specifier: workspace:*
version: link:../../crypto/polyfill
rfc4648:
specifier: 'catalog:'
version: 1.5.3
@@ -4084,6 +4093,9 @@ importers:
'@pnpm/crypto.base32-hash':
specifier: workspace:*
version: link:../../packages/crypto.base32-hash
'@pnpm/crypto.polyfill':
specifier: workspace:*
version: link:../../crypto/polyfill
'@pnpm/dependency-path':
specifier: workspace:*
version: link:../../packages/dependency-path
@@ -6269,6 +6281,9 @@ importers:
'@pnpm/core-loggers':
specifier: workspace:*
version: link:../../packages/core-loggers
'@pnpm/crypto.polyfill':
specifier: workspace:*
version: link:../../crypto/polyfill
'@pnpm/error':
specifier: workspace:*
version: link:../../packages/error
@@ -6520,6 +6535,9 @@ importers:
reviewing/list:
dependencies:
'@pnpm/crypto.polyfill':
specifier: workspace:*
version: link:../../crypto/polyfill
'@pnpm/read-package-json':
specifier: workspace:*
version: link:../../pkg-manifest/read-package-json
@@ -7521,6 +7539,9 @@ importers:
'@pnpm/create-cafs-store':
specifier: workspace:*
version: link:../store/create-cafs-store
'@pnpm/crypto.polyfill':
specifier: workspace:*
version: link:../crypto/polyfill
'@pnpm/error':
specifier: workspace:*
version: link:../packages/error

View File

@@ -36,6 +36,7 @@
"dependencies": {
"@pnpm/constants": "workspace:*",
"@pnpm/core-loggers": "workspace:*",
"@pnpm/crypto.polyfill": "workspace:*",
"@pnpm/error": "workspace:*",
"@pnpm/fetching-types": "workspace:*",
"@pnpm/graceful-fs": "workspace:*",

View File

@@ -1,6 +1,6 @@
import crypto from 'crypto'
import { promises as fs } from 'fs'
import path from 'path'
import * as crypto from '@pnpm/crypto.polyfill'
import { PnpmError } from '@pnpm/error'
import { logger } from '@pnpm/logger'
import gfs from '@pnpm/graceful-fs'
@@ -270,7 +270,7 @@ function clearMeta (pkg: PackageMeta): PackageMeta {
function encodePkgName (pkgName: string): string {
if (pkgName !== pkgName.toLowerCase()) {
return `${pkgName}_${crypto.createHash('md5').update(pkgName).digest('hex')}`
return `${pkgName}_${crypto.hash('md5', pkgName, 'hex')}`
}
return pkgName
}

View File

@@ -12,6 +12,9 @@
{
"path": "../../__utils__/test-fixtures"
},
{
"path": "../../crypto/polyfill"
},
{
"path": "../../fs/graceful-fs"
},

View File

@@ -34,6 +34,7 @@
},
"homepage": "https://github.com/pnpm/pnpm/blob/main/reviewing/list#readme",
"dependencies": {
"@pnpm/crypto.polyfill": "workspace:*",
"@pnpm/read-package-json": "workspace:*",
"@pnpm/read-project-manifest": "workspace:*",
"@pnpm/reviewing.dependencies-hierarchy": "workspace:*",

View File

@@ -1,6 +1,6 @@
import * as crypto from '@pnpm/crypto.polyfill'
import { type DependenciesHierarchy, type PackageNode } from '@pnpm/reviewing.dependencies-hierarchy'
import { type PackageDependencyHierarchy } from './types'
import { createHash } from 'crypto'
export function pruneDependenciesTrees (trees: PackageDependencyHierarchy[] | null, limit: number): PackageDependencyHierarchy[] {
if (trees === null) {
@@ -57,7 +57,7 @@ export function pruneDependenciesTrees (trees: PackageDependencyHierarchy[] | nu
for (const node of path) {
pathSoFar += `${node.name}@${node.version},`
const id = createHash('sha256').update(pathSoFar).digest('hex')
const id = crypto.hash('sha256', pathSoFar, 'hex')
let existingNode = map.get(id)
if (!existingNode) {

View File

@@ -12,6 +12,9 @@
{
"path": "../../__utils__/test-fixtures"
},
{
"path": "../../crypto/polyfill"
},
{
"path": "../../packages/types"
},

View File

@@ -34,6 +34,7 @@
"dependencies": {
"@pnpm/cafs-types": "workspace:*",
"@pnpm/create-cafs-store": "workspace:*",
"@pnpm/crypto.polyfill": "workspace:*",
"@pnpm/error": "workspace:*",
"@pnpm/exec.pkg-requires-build": "workspace:*",
"@pnpm/fs.hard-link-dir": "workspace:*",

View File

@@ -1,9 +1,9 @@
import path from 'path'
import fs from 'fs'
import gfs from '@pnpm/graceful-fs'
import * as crypto from 'crypto'
import { type Cafs } from '@pnpm/cafs-types'
import { createCafsStore } from '@pnpm/create-cafs-store'
import * as crypto from '@pnpm/crypto.polyfill'
import { pkgRequiresBuild } from '@pnpm/exec.pkg-requires-build'
import { hardLinkDir } from '@pnpm/fs.hard-link-dir'
import {
@@ -129,7 +129,7 @@ function addTarballToStore ({ buffer, cafsDir, integrity, filesIndexFile }: Tarb
// Compensate for the possibility of non-uniform Base64 padding
const normalizedRemoteHash: string = Buffer.from(integrityHash, 'base64').toString('hex')
const calculatedHash: string = crypto.createHash(algo).update(buffer).digest('hex')
const calculatedHash: string = crypto.hash(algo, buffer, 'hex')
if (calculatedHash !== normalizedRemoteHash) {
return {
status: 'error',

View File

@@ -9,6 +9,9 @@
"../../__typings__/**/*.d.ts"
],
"references": [
{
"path": "../crypto/polyfill"
},
{
"path": "../exec/pkg-requires-build"
},