test: enforce package size (#4098)

* build: use fewer babel versions

* build: dedup

* test: test deps dedups

* fix: test.yml

* fix: typo

* test: failing

* fix: dedup

* fix: dedup

* test: comment dedup tests

* chore: whitespace

* test: package size

* build: scripts

* test: update test-size

* docs: CONTRIBUTING
This commit is contained in:
Zach Pomerantz 2023-03-07 09:27:20 -08:00 committed by GitHub
parent e9fc55550d
commit a7c6ce499d
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
6 changed files with 92 additions and 8 deletions

@ -36,13 +36,12 @@ jobs:
fail_ci_if_error: false
verbose: true
cypress-build:
build:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v3
- uses: ./.github/actions/setup
- run: yarn prepare
- run: yarn build
- uses: actions/upload-artifact@v2
with:
@ -50,6 +49,24 @@ jobs:
path: build
if-no-files-found: error
size-tests:
needs: [build]
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v3
- uses: ./.github/actions/setup
- uses: actions/download-artifact@v2
with:
name: build
path: build
- run: yarn test:size
cypress-build:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v3
- uses: ./.github/actions/setup
- uses: actions/cache@v3
id: cypress-cache
with:
@ -59,7 +76,7 @@ jobs:
run: yarn cypress install
cypress-test-matrix:
needs: cypress-build
needs: [build, cypress-build]
runs-on: ubuntu-latest
strategy:
fail-fast: false
@ -96,7 +113,7 @@ jobs:
# Included as a single job to check against for cypress test success, as cypress runs in a matrix.
cypress-tests:
needs: cypress-test-matrix
needs: [cypress-test-matrix]
runs-on: ubuntu-latest
steps:
- run: echo 'Finished cypress tests https\://dashboard.cypress.io/projects/yp82ef'

@ -64,6 +64,14 @@ To run _all_ cypress integration tests _from the command line_:
yarn cypress:run
```
## Adding a new dependency
Adding many new dependencies would cause bloat, so we have a test to guard against this: `scripts/test-size.js`. This will run as part of CI with every PR.
If you *need* to add a new dependency, and it causes the generated build to exceed its size quota, you'll need to increase the quota. Do so in `scripts/test-size.js`.
You can also run the test on your last build using `yarn build && yarn test:size`. If you exceed the size quota, it will let you know what to do :).
## Engineering standards
Code merged into the `main` branch of this repository should adhere to high standards of correctness and maintainability.

@ -8,11 +8,11 @@
"contracts:compile:abi": "typechain --target ethers-v5 --out-dir src/abis/types \"./src/abis/**/*.json\"",
"contracts:compile:v3": "typechain --target ethers-v5 --out-dir src/types/v3 \"./node_modules/@uniswap/**/artifacts/contracts/**/*[!dbg].json\"",
"contracts:compile": "yarn contracts:compile:abi && yarn contracts:compile:v3",
"graphql:fetch": "node fetch-schema.js",
"graphql:fetch": "node scripts/fetch-schema.js",
"graphql:generate:data": "graphql-codegen --config apollo-codegen.ts",
"graphql:generate:thegraph": "graphql-codegen --config apollo-codegen_thegraph.ts",
"graphql:generate": "yarn graphql:generate:data && yarn graphql:generate:thegraph",
"prei18n:extract": "node prei18n-extract.js",
"prei18n:extract": "node scripts/prei18n-extract.js",
"i18n:extract": "lingui extract --locale en-US",
"i18n:compile": "yarn i18n:extract && lingui compile",
"i18n:pseudo": "lingui extract --locale pseudo && lingui compile",
@ -23,6 +23,7 @@
"deduplicate": "yarn-deduplicate --strategy=highest",
"lint": "yarn eslint .",
"test": "craco test --coverage",
"test:size": "node scripts/test-size.js",
"cypress:open": "cypress open --browser chrome --e2e",
"cypress:run": "cypress run --browser chrome --e2e",
"postinstall": "patch-package"

@ -3,8 +3,8 @@
require('dotenv').config({ path: '.env.production' })
const { exec } = require('child_process')
const dataConfig = require('./graphql.config')
const thegraphConfig = require('./graphql_thegraph.config')
const dataConfig = require('../graphql.config')
const thegraphConfig = require('../graphql_thegraph.config')
function fetchSchema(url, outputFile) {
exec(

58
scripts/test-size.js Normal file

@ -0,0 +1,58 @@
/* eslint-disable no-undef */
const assert = require('assert')
const chalk = require('chalk')
const fs = require('fs')
const gzipSize = require('gzip-size').sync
const path = require('path')
const buildDir = path.join(__dirname, '../build')
let entrypoints
try {
entrypoints = require(path.join(buildDir, 'asset-manifest.json')).entrypoints
} catch (e) {
console.log(chalk.yellow('You must build first: `yarn build`'))
process.exit(1)
}
// The last recorded size for these assets, as reported by `yarn build`.
const MAX_SIZE_MAIN_KB = 361.36
// This is the async-loaded js, called <number>.<hash>.js, with a matching css file.
const MAX_SIZE_ENTRY_MB = 1.38
const SIZE_TOLERANCE_KB = 5
const jsEntrypoints = entrypoints.filter((entrypoint) => entrypoint.endsWith('js'))
assert(jsEntrypoints.length === 3)
let fail = false
console.log('File sizes after gzip:\n')
jsEntrypoints.forEach((entrypoint) => {
const name = entrypoint.match(/\/([\w\d-]*)\./)[1]
const size = gzipSize(fs.readFileSync(path.join(buildDir, entrypoint)))
let maxSize = MAX_SIZE_ENTRY_MB * 1024 * 1024
if (name === 'runtime-main') {
return
} else if (name === 'main') {
maxSize = MAX_SIZE_MAIN_KB * 1024
}
maxSize += SIZE_TOLERANCE_KB * 1024
if (maxSize > size) {
console.log(chalk.green(`\t${toKb(maxSize)}\t${entrypoint}`))
} else {
console.log(chalk.red(`\t${toKb(maxSize)}\t${entrypoint}`), '\tdid you import an unnecessary dependency?')
fail = true
}
})
if (fail) {
console.log(chalk.yellow('\nOne or more of your files has grown too large.'))
console.log(chalk.yellow('Reduce the file size or update the size limit (in scripts/test-size.js)'))
process.exit(1)
}
function toKb(bytes) {
return ((bytes / 1024).toFixed(2) + ' kB').padEnd(8)
}