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

github(workflows): add package size checks, add auto demo deploy #1048

Merged
merged 45 commits into from
Feb 9, 2021
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
45 commits
Select commit Hold shift + click to select a range
7754a8b
internal(deps): add deps for ts-node and filesize computation
williaster Feb 4, 2021
f385cdf
internal(node): add tsconfig for node
williaster Feb 4, 2021
6b67007
build: add computeBuildSizes script
williaster Feb 4, 2021
96b1e96
build: add compareBuildSizes, upsertPullRequestComment scripts
williaster Feb 4, 2021
b778c4f
build: update computeBuildSizes output file
williaster Feb 5, 2021
65d7f0b
build: add deploy-demo script
williaster Feb 5, 2021
894c506
github(workflows/ci): add Package sizes + Deploy gallery steps
williaster Feb 5, 2021
cb085cc
github(workflows/ci): add pull_request checks to happo, package sizes
williaster Feb 5, 2021
06f90a2
deps(dev): add @types/node-fetch
williaster Feb 5, 2021
85d18be
deps: update yarn.lock
williaster Feb 5, 2021
c055393
type(scripts/upsertPullRequestComment): fix comment type
williaster Feb 5, 2021
6703ca8
github(workflows): separate CI into push + pull_request
williaster Feb 5, 2021
fdcc602
deps(dev): add @octokit/rest
williaster Feb 5, 2021
1efd7c8
fix(workflows/pull_request): add needed variables for upsertPullReque…
williaster Feb 5, 2021
91f4e6e
commit to kick workflow
williaster Feb 5, 2021
a861a39
github(workflows): fix package size report job
williaster Feb 5, 2021
f50dff2
github(workflow): fix GITHUB_REPOSITORY/ACTOR variable syntax
williaster Feb 5, 2021
f01184d
fix(scripts/upsertPullRequestComment): better types
williaster Feb 5, 2021
8dd0720
fix(scripts/compareBuildSizes): log errors
williaster Feb 5, 2021
e21bc08
debug(scripts//upsertPullRequestComment): add more debug logs
williaster Feb 5, 2021
2169ed7
debug(scripts/upsertPullRequestComment): add more debug logs
williaster Feb 5, 2021
42509e4
fix(/workflows/pull_request): remove debug logging
williaster Feb 5, 2021
734973e
github(workflows): update branches for testing
williaster Feb 5, 2021
32deeda
fix(workflows/push)
williaster Feb 5, 2021
e8a955c
fix(scripts/upsertPullRequestComment): fix bot user login check
williaster Feb 5, 2021
9609b2f
deps(demo, annotation, tooltip): react-measure@2.0.3
williaster Feb 5, 2021
e6d31c5
fix(demo/axis,pattern,xychart): fix window check for ssr
williaster Feb 5, 2021
0009880
fix(/workflows/push): rewrite gallery deploy job to fix credentials
williaster Feb 5, 2021
ff77c3e
fix(workflows/push/gallery): try to fix credentials
williaster Feb 5, 2021
6cb73a3
fix(github/workflows/push): try https for gallery push
williaster Feb 5, 2021
2fdee13
fix(workflows/push): tweak https syntax
williaster Feb 5, 2021
521b296
fix(workflows/push): try github-pages-deploy-action
williaster Feb 5, 2021
72b182c
fix(workflows/push): don't use working-directory with uses
williaster Feb 5, 2021
82bfeab
fix(workflows/push): try changing persist-credentials mid-workflow
williaster Feb 5, 2021
ff3a7b7
fix(workflows/push): more changes
williaster Feb 5, 2021
6e71972
fix(workflows/push): try worktree approach
williaster Feb 6, 2021
ed6c6bf
fix(workflows/push): build gallery on master
williaster Feb 6, 2021
b6734d3
fix(workflows/push): add out/ contents pre-commit
williaster Feb 6, 2021
16eac02
fix(workflows/push): fix credentials
williaster Feb 6, 2021
3bed467
fix(workflows/push): try not master
williaster Feb 6, 2021
ddd77a9
fix(workflows/push): try not master take 2
williaster Feb 6, 2021
da1b374
fix(workflows/push): we have a winner
williaster Feb 9, 2021
1bc79d1
fix(workflows/push,pull_request): final final
williaster Feb 9, 2021
d503be5
fix(workflows/push): match 📡 emoji across workflows 🙄
williaster Feb 9, 2021
160db5c
type(scripts/upsertPullRequestComment): fix types
williaster Feb 9, 2021
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
27 changes: 17 additions & 10 deletions .github/workflows/ci.yml → .github/workflows/pull_request.yml
Original file line number Diff line number Diff line change
@@ -1,16 +1,14 @@
name: CI
name: Pull request

on:
push:
branches: [master]
pull_request:
branches: [master]

jobs:
build:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v2
- uses: actions/checkout@v2 # checkout visx + this commit
- uses: actions/setup-node@v1
with:
node-version: '12'
Expand All @@ -26,30 +24,39 @@ jobs:
restore-keys: |
${{ runner.os }}-yarn-

- name: Install dependencies
- name: 📡 Install dependencies
run: yarn install --frozen-lockfile --ignore-engines

- name: Build packages
- name: 🛠 Build packages
run: yarn build

- name: Run jest
- name: 🧪 Run jest
run: yarn jest -w 4
env:
CI: true
COVERAGE: true

- name: Report code coverage
- name: 📈 Report code coverage
uses: coverallsapp/github-action@v1.1.1
with:
github-token: ${{ secrets.GITHUB_TOKEN }}

- name: Run lint
- name: Run lint
run: yarn lint

- name: Run happo
- name: 🦛 Run happo
run: yarn run happo-ci-github-actions
working-directory: './packages/visx-demo/'
env:
HAPPO_API_KEY: ${{ secrets.HAPPO_API_KEY }}
HAPPO_API_SECRET: ${{ secrets.HAPPO_API_SECRET }}
HAPPO_COMMAND: '../../node_modules/happo.io/build/cli.js'

- name: 📐 Report package sizes
run: yarn build:sizes && yarn check:sizes
# add needed variables for posting on the PR via octokit
env:
GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }}
PR_NUMBER: ${{ github.event.pull_request.number }}
GITHUB_REPOSITORY: $GITHUB_REPOSITORY
GITHUB_ACTOR: $GITHUB_ACTOR
70 changes: 70 additions & 0 deletions .github/workflows/push.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,70 @@
name: Push

on:
push:
branches: [master]

jobs:
build:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v2 # checkout visx + this commit
- uses: actions/setup-node@v1
with:
node-version: '12'

- name: Get yarn cache directory path
id: yarn-cache-dir-path
run: echo "::set-output name=dir::$(yarn cache dir)"
- uses: actions/cache@v1
id: yarn-cache # use this to check for `cache-hit` (`steps.yarn-cache.outputs.cache-hit != 'true'`)
with:
path: ${{ steps.yarn-cache-dir-path.outputs.dir }}
key: ${{ runner.os }}-yarn-${{ hashFiles('**/yarn.lock') }}
restore-keys: |
${{ runner.os }}-yarn-

- name: 📡 Install dependencies
run: yarn install --frozen-lockfile --ignore-engines

- name: 🛠 Build packages
run: yarn build

- name: 📐 Commit package sizes
run: |
yarn build:sizes
git config user.name github-actions
git config user.email github-actions@github.com
git add .
git commit -m "build(${GITHUB_SHA}): auto-commit package sizes"
git push

- name: 🚀 Build and deploy gallery
# below we
# - setup git credentials provided via actions/checkout@v2
# - initialize gh-pages-branch as an orphan branch so we don't build history
# - checkout the current commit and create gh-pages-root-dir/ as a new worktree
# - outside that directory HEAD is detached at $GITHUB_SHA
# - within that directory we are on the gh-pages-branch we just initialized
# *worktree initialization should be in a root dir, otherwise the worktree inherits nested directories
# - build the static next.js site and copy the output into gh-pages-root-dir/
# - we can't output directly into gh-pages-root-dir/ because next wipes the folder including .git
# - commit the demo site within gh-pages-root-dir/ onto the gh-pages-branch
# - push gh-pages-branch to visx as gh-pages. we overwrite history every time so it must be forced
run: |
git config user.name github-actions
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I usually use this package to handle deployment to github pages.
Would it simplify the script here?
https://www.npmjs.com/package/gh-pages

"scripts": {
  "deploy": "gh-pages -d dist"
}
yarn build
yarn deploy

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Currently we deploy to gh-pages with a simple script in @visx/demo that is similar to these commands. the complexity comes from the creation of a new git worktree without history in the action environment.

tbh I spent so much time on this already I'd rather just leave it. I tried a gh-pages action someone made and it worked, but it requires special handling of credentials which then causes the package size commit to fail. so would have to duplicate the yarn && yarn build steps multiple times which isn't ideal.

git config user.email github-actions@github.com
git checkout --orphan gh-pages-branch
git reset --hard
touch .nojekyll
git add .nojekyll
git commit -m "bot(${GITHUB_SHA}): initialize gh-pages branch"
git checkout "$GITHUB_SHA"
git worktree add gh-pages-root-dir gh-pages-branch
cd ./packages/visx-demo/
yarn build
mv -v out/* ../../gh-pages-root-dir/
cd ../../gh-pages-root-dir/
git add .
git commit -m "bot(${GITHUB_SHA}): build gh-pages"
git push -f "https://$GITHUB_ACTOR:$GITHUB_TOKEN@github.com/$GITHUB_REPOSITORY.git" HEAD:gh-pages
27 changes: 20 additions & 7 deletions package.json
Original file line number Diff line number Diff line change
Expand Up @@ -30,23 +30,29 @@
],
"private": true,
"scripts": {
"build": "yarn run babel && yarn run type:dts",
"build-one": "nimbus babel --clean",
"babel": "yarn run babel:cjs && yarn run babel:esm",
"babel:cjs": "nimbus babel --clean --workspaces=\"@visx/!(demo)\"",
"babel:esm": "nimbus babel --clean --workspaces=\"@visx/!(demo)\" --esm",
"build": "yarn run babel && yarn run type",
"build-one": "echo 'build-one has been replaced with build:workspace' & exit 1",
"build:sizes": "yarn run ts ./scripts/computeBuildSizes.ts",
"build:workspace": "nimbus babel --clean",
"check:sizes": "yarn run ts ./scripts/compareBuildSizes.ts",
"clean": "rm -rf ./packages/**/{lib,esm}",
"format": "yarn run prettier --write",
"jest": "NODE_ENV=test nimbus jest --coverage --verbose",
"lint": "nimbus eslint",
"lint:fix": "yarn run lint --fix",
"prepare-release": "git checkout master && git pull --rebase origin master && lerna updated",
"prettier": "nimbus prettier",
"release": "yarn run prepare-release && lerna publish --exact",
"setup": "yarn run build",
"test": "yarn run jest",
"type:dts": "nimbus typescript --build --reference-workspaces",
"type-one": "nimbus typescript --build",
"prepare-release": "git checkout master && git pull --rebase origin master && lerna updated",
"release": "yarn run prepare-release && lerna publish --exact"
"ts": "ts-node --project ./tsconfig.node.json",
Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

ts-node allows running TypeScript scripts. requires the TS config to understand commonjs module format.

"type": "nimbus typescript --build --reference-workspaces",
"type-one": "echo 'type-one has been replaced with type:workspace' & exit 1",
"type:dts": "echo 'type:dts has been replaced with type' & exit 1",
"type:workspace": "nimbus typescript --build"
},
"devDependencies": {
"@airbnb/config-babel": "^2.1.3",
Expand All @@ -55,26 +61,33 @@
"@airbnb/config-prettier": "^2.0.4",
"@airbnb/config-typescript": "^2.1.2",
"@airbnb/nimbus": "^2.1.3",
"@octokit/rest": "18.1.0",
"@types/enzyme": "^3.10.3",
"@types/jest": "^24.0.18",
"@types/jsdom": "^12.2.4",
"@types/node-fetch": "1.6.9",
"@types/react-test-renderer": "^16.9.0",
"@types/webpack": "^4.41.17",
"chalk": "4.1.0",
"coveralls": "^3.0.6",
"enzyme": "^3.10.0",
"enzyme-adapter-react-16": "^1.14.0",
"enzyme-to-json": "^3.4.0",
"fast-glob": "3.2.5",
"filesize": "6.1.0",
"fs-jetpack": "^1.3.0",
"husky": "^3.0.0",
"jest-mock-console": "^1.0.1",
"lerna": "^3.15.0",
"marked": "^0.7.0",
"node-fetch": "2.6.1",
"raf": "^3.4.0",
"react": "^15.0.0-0 || ^16.0.0-0",
"react-dom": "^15.0.0-0 || ^16.0.0-0",
"react-test-renderer": "^16.8.6",
"regenerator-runtime": "^0.10.5",
"timezone-mock": "^1.1.0"
"timezone-mock": "^1.1.0",
"ts-node": "9.1.1"
},
"workspaces": [
"./packages/*"
Expand Down
2 changes: 1 addition & 1 deletion packages/visx-annotation/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -40,7 +40,7 @@
"@visx/text": "1.3.0",
"classnames": "^2.2.5",
"prop-types": "^15.5.10",
"react-use-measure": "2.0.1"
"react-use-measure": "^2.0.3"
},
"devDependencies": {
"resize-observer-polyfill": "^1.5.1"
Expand Down
2 changes: 1 addition & 1 deletion packages/visx-demo/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -68,7 +68,7 @@
"@visx/xychart": "1.4.0",
"@visx/zoom": "1.3.0",
"@zeit/next-css": "^1.0.1",
"babel-loader": "8.2.2",
"babel-loader": "^8.2.2",
"classnames": "^2.2.5",
"d3-array": "^1.1.1",
"d3-collection": "^1.0.4",
Expand Down
3 changes: 2 additions & 1 deletion packages/visx-demo/src/sandboxes/visx-axis/Example.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -67,7 +67,8 @@ export default function Example({
showControls = true,
}: AxisProps) {
// use non-animated components if prefers-reduced-motion is set
const prefersReducedMotionQuery = window?.matchMedia('(prefers-reduced-motion: reduce)');
const prefersReducedMotionQuery =
Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

window.? was throwing in next's SSR environment

typeof window === 'undefined' ? false : window.matchMedia('(prefers-reduced-motion: reduce)');
const prefersReducedMotion = !prefersReducedMotionQuery || !!prefersReducedMotionQuery.matches;
const [useAnimatedComponents, setUseAnimatedComponents] = useState(!prefersReducedMotion);

Expand Down
3 changes: 2 additions & 1 deletion packages/visx-demo/src/sandboxes/visx-pattern/Example.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -120,7 +120,8 @@ const Patterns: React.FC<{ id: string; prefersReducedMotion?: boolean }>[] = [

export default function Example({ width, height, margin = defaultMargin }: PatternProps) {
// use non-animated components if prefers-reduced-motion is set
const prefersReducedMotionQuery = window?.matchMedia('(prefers-reduced-motion: reduce)');
const prefersReducedMotionQuery =
typeof window === 'undefined' ? false : window.matchMedia('(prefers-reduced-motion: reduce)');
const prefersReducedMotion = !prefersReducedMotionQuery || !!prefersReducedMotionQuery.matches;

const numColumns = 3;
Expand Down
Original file line number Diff line number Diff line change
@@ -1,4 +1,5 @@
export default function userPrefersReducedMotion() {
const prefersReducedMotionQuery = window?.matchMedia('(prefers-reduced-motion: reduce)');
const prefersReducedMotionQuery =
typeof window === 'undefined' ? false : window.matchMedia('(prefers-reduced-motion: reduce)');
return !prefersReducedMotionQuery || !!prefersReducedMotionQuery.matches;
}
2 changes: 1 addition & 1 deletion packages/visx-tooltip/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -33,7 +33,7 @@
"@visx/bounds": "1.0.0",
"classnames": "^2.2.5",
"prop-types": "^15.5.10",
"react-use-measure": "2.0.1"
"react-use-measure": "^2.0.3"
},
"peerDependencies": {
"react": "^16.8.0-0",
Expand Down
124 changes: 124 additions & 0 deletions scripts/compareBuildSizes.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,124 @@
import fs from 'fs';
import size from 'filesize';
import chalk from 'chalk';
import fetch from 'node-fetch';
import upsertPullRequestComment from './upsertPullRequestComment';
import { PACKAGE_SIZES_FILENAME } from './computeBuildSizes';

type StatMap = {
[pkg: string]: {
[dir: string]: number;
};
};

function calculateDiff(prev: number, next: number): number {
return (next - prev) / prev;
}

function formatDiff(diff: number): string {
const sum = diff * 100;
const percent = sum.toFixed(1);

// Smaller
if (percent.startsWith('-')) {
return `${sum < -10 ? ':small_red_triangle_down: ' : ''}${percent}%`;
}

// Larger
return `${sum > 10 ? ':small_red_triangle: ' : ''}+${percent}%`;
}

async function compareBuildSizes() {
const nextSizes: StatMap = JSON.parse(fs.readFileSync(PACKAGE_SIZES_FILENAME, 'utf8'));
let prevSizes: StatMap = {};
let sameBuild = false;

try {
const masterFileSizesRequest = await fetch(
`https://raw.githubusercontent.com/airbnb/visx/master/${PACKAGE_SIZES_FILENAME}`,
);

prevSizes = await masterFileSizesRequest.json();
} catch (error) {
console.log(`Could not fetch file ${PACKAGE_SIZES_FILENAME} from master. Aborting.`);
console.log(error.message);

prevSizes = nextSizes;
sameBuild = true;
}

function getPrevSize(name: string, type: string) {
return (prevSizes[name] && prevSizes[name][type]) || 0;
}

const output: string[] = [
'### Size Changes',
'| Package | Diff | ESM | Prev ESM | CJS | Prev CJS |',
'| --- | ---: | ---: | ---: | ---: | ---: |',
];
const rows: string[] = [];

Object.entries(nextSizes).forEach(([pkgName, stats]) => {
const prevEsm = getPrevSize(pkgName, 'esm');
const prevLib = getPrevSize(pkgName, 'lib');
const diff = calculateDiff(prevEsm, stats.esm);

if (!isFinite(diff) || diff === 0 || diff === 0.0) {
return;
}

const row = [
pkgName,
formatDiff(diff),
size(stats.esm),
prevEsm === 0 ? 'N/A' : size(prevEsm),
size(stats.lib),
prevLib === 0 ? 'N/A' : size(prevLib),
];

rows.push(`| ${row.join(' | ')} |`);
});

// Don't post anything if no changes
if (rows.length === 0) {
return;
}

// Sort rows before joining to output
rows.sort();

output.push(...rows);
output.push('> Compared to master. File sizes are unminified and ungzipped.');

// Show dumps for easier debugging
if (!sameBuild) {
output.push(`<details>
<summary>View raw build stats</summary>

#### Previous (master)
\`\`\`json
${JSON.stringify(prevSizes, null, 2)}
\`\`\`

#### Current
\`\`\`json
${JSON.stringify(nextSizes, null, 2)}
\`\`\`
</details>`);
}

// Leave a comment on the PR
const breakdown = output.join('\n');

try {
await upsertPullRequestComment('### Size Changes', breakdown);
} catch (error) {
console.log('Could not post size stats', breakdown);
console.error(error);
}
}

compareBuildSizes().catch(error => {
console.error(chalk.red(error.message));
process.exitCode = 1;
});
Loading