Skip to content

Commit dc200dd

Browse files
authored
ci: create pr preview and e2e workflow (#222)
AB#3559759
1 parent 5fdf507 commit dc200dd

19 files changed

Lines changed: 1721 additions & 58 deletions

.github/workflows/e2e.yml

Lines changed: 81 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,81 @@
1+
name: E2E
2+
on:
3+
push:
4+
branches:
5+
- master
6+
- '[0-9]+.x.x'
7+
pull_request:
8+
branches:
9+
- master
10+
- '[0-9]+.x.x'
11+
12+
concurrency:
13+
group: ${{ github.workflow }}-${{ github.event_name == 'push' && github.run_number || github.head_ref || github.ref_name || github.event.ref }}
14+
cancel-in-progress: true
15+
16+
env:
17+
NX_CLOUD_DISTRIBUTED_EXECUTION: 'false'
18+
CYPRESS_VERIFY_TIMEOUT: 120000
19+
PERCY_BROWSER_EXECUTABLE: /usr/bin/chromium
20+
PERCY_SKIP_UPDATE_CHECK: 'true'
21+
PUPPETEER_EXECUTABLE_PATH: /usr/bin/chromium
22+
PUPPETEER_SKIP_CHROMIUM_DOWNLOAD: 'true'
23+
SB_CHROMIUM_PATH: /usr/bin/chromium
24+
25+
jobs:
26+
e2e:
27+
runs-on: ubuntu-latest
28+
steps:
29+
- name: Checkout code
30+
uses: actions/checkout@v5
31+
with:
32+
path: 'skyux-icons'
33+
fetch-depth: '0'
34+
token: '${{ secrets.GH_PERSONAL_ACCESS_TOKEN }}'
35+
- name: Checkout skyux
36+
uses: actions/checkout@v5
37+
with:
38+
repository: 'blackbaud/skyux'
39+
ref: 'main'
40+
path: 'skyux'
41+
token: '${{ secrets.GH_PERSONAL_ACCESS_TOKEN }}'
42+
- name: Set up Node.js
43+
uses: actions/setup-node@v5
44+
with:
45+
node-version-file: 'skyux/.nvmrc'
46+
- name: Install dependencies
47+
run: npm ci
48+
working-directory: 'skyux-icons'
49+
- name: Build project
50+
run: npm run build
51+
working-directory: 'skyux-icons'
52+
- name: Install skyux
53+
run: npm ci
54+
working-directory: 'skyux'
55+
env:
56+
CYPRESS_INSTALL_BINARY: 0
57+
- name: Install Cypress
58+
run: |
59+
set -euxo pipefail
60+
npx cypress install
61+
npx cypress verify
62+
working-directory: 'skyux'
63+
- name: Build Storybooks
64+
run: npx nx build-storybook icon-storybook --no-dte
65+
working-directory: 'skyux'
66+
env:
67+
NX_CLOUD_ACCESS_TOKEN: '${{ secrets.NX_CLOUD_ACCESS_TOKEN }}'
68+
- name: Apply icon preview link tag
69+
run: |
70+
for idx in dist/storybook/*/iframe.html; do
71+
echo "Adding skyux-icons.svg to $idx"
72+
sed -i'' 's~</head>~<link rel="prefetch" href="./skyux-icons.svg" class="skyux-icons-preview"></head>~' $idx
73+
cp -v ../skyux-icons/dist/assets/svg/skyux-icons.svg $(dirname $idx)/
74+
done
75+
working-directory: 'skyux'
76+
- name: Run e2e tests
77+
run: |
78+
npx percy exec -- npx nx e2e icon-storybook-e2e -c prebuilt --no-dte --skip-nx-cache
79+
working-directory: 'skyux'
80+
env:
81+
PERCY_TOKEN: '${{ secrets.PERCY_TOKEN }}'

.github/workflows/pages.yml

Lines changed: 101 additions & 37 deletions
Original file line numberDiff line numberDiff line change
@@ -1,73 +1,137 @@
1+
name: Pages
12
on:
2-
push:
3-
branches:
4-
- master
53
pull_request:
64
branches:
75
- master
6+
- '[0-9]+.x.x'
7+
88
permissions:
9+
actions: read
910
contents: read
1011
pages: write
1112
id-token: write
13+
1214
concurrency:
1315
group: pages
1416
cancel-in-progress: false
1517

16-
jobs:
17-
build:
18-
runs-on: ubuntu-latest
19-
steps:
20-
- name: Checkout code
21-
uses: actions/checkout@v4
22-
- name: Set up Node.js
23-
uses: actions/setup-node@v4
24-
with:
25-
node-version-file: '.nvmrc'
26-
cache: 'npm'
27-
- name: Install dependencies
28-
run: npm ci
29-
- name: Build project
30-
run: npm run build
31-
- name: Upload artifact
32-
uses: actions/upload-artifact@v4
33-
if: github.event_name == 'pull_request'
34-
with:
35-
name: pr-${{ github.event.pull_request.number }}
36-
path: './dist'
37-
retention-days: 30
38-
if-no-files-found: error
18+
env:
19+
NX_CLOUD_DISTRIBUTED_EXECUTION: 'false'
3920

40-
deploy:
21+
jobs:
22+
pages:
4123
environment:
4224
name: github-pages
4325
url: ${{ steps.deployment.outputs.page_url }}
4426
runs-on: ubuntu-latest
45-
needs: [build]
4627
steps:
4728
- name: Checkout code
48-
uses: actions/checkout@v4
29+
uses: actions/checkout@v5
4930
with:
50-
ref: master
31+
path: 'skyux-icons'
32+
token: '${{ secrets.GH_PERSONAL_ACCESS_TOKEN }}'
33+
- name: Checkout skyux
34+
uses: actions/checkout@v5
35+
with:
36+
repository: 'blackbaud/skyux'
37+
ref: 'main'
38+
path: 'skyux'
39+
token: '${{ secrets.GH_PERSONAL_ACCESS_TOKEN }}'
5140
- name: Set up Node.js
52-
uses: actions/setup-node@v4
41+
uses: actions/setup-node@v5
5342
with:
54-
node-version-file: '.nvmrc'
55-
cache: 'npm'
43+
node-version-file: 'skyux/.nvmrc'
5644
- name: Install dependencies
5745
run: npm ci
46+
working-directory: 'skyux-icons'
5847
- name: Build project
5948
run: npm run build
60-
- name: Download artifact
61-
uses: actions/download-artifact@v4
49+
working-directory: 'skyux-icons'
50+
- name: Install skyux
51+
run: npm ci
52+
working-directory: 'skyux'
53+
env:
54+
CYPRESS_INSTALL_BINARY: 0
55+
- name: Build Storybooks
56+
run: npx nx run-many -t build-storybook --projects=tag:icons-preview --no-dte
57+
working-directory: 'skyux'
58+
env:
59+
NX_CLOUD_ACCESS_TOKEN: '${{ secrets.NX_CLOUD_ACCESS_TOKEN }}'
60+
- name: Build playground
61+
run: npx nx run playground:build --no-dte && mkdir -pv dist/preview-pages
62+
working-directory: 'skyux'
63+
env:
64+
NX_CLOUD_ACCESS_TOKEN: '${{ secrets.NX_CLOUD_ACCESS_TOKEN }}'
65+
- name: Retrieve other preview sites
66+
uses: actions/download-artifact@v5
6267
with:
6368
github-token: '${{ secrets.GH_PERSONAL_ACCESS_TOKEN }}'
64-
path: './dist'
69+
path: skyux/dist/preview-pages/
6570
pattern: 'pr-*'
6671
repository: '${{ github.repository }}'
72+
- name: Create preview site for PR ${{ github.event.number }}
73+
run: |
74+
rm -rfv dist/preview-pages/pr-${{ github.event.number }}
75+
mkdir -pv dist/preview-pages/pr-${{ github.event.number }}/storybooks
76+
mv -v dist/apps/* dist/preview-pages/pr-${{ github.event.number }}/
77+
mv -v dist/storybook/* dist/preview-pages/pr-${{ github.event.number }}/storybooks/
78+
for idx in dist/preview-pages/pr-${{ github.event.number }}/*/index.html; do
79+
APP_BASE_HREF="skyux-icons/pr-${{ github.event.number }}/$(basename $(dirname $idx))"
80+
echo "Setting base href to ${APP_BASE_HREF} for $idx"
81+
sed -i'' 's~<base href="/"~<base href="/'${APP_BASE_HREF}'/"~g' $idx
82+
done
83+
working-directory: 'skyux'
84+
- name: Apply icon preview link tag
85+
run: |
86+
for idx in dist/preview-pages/pr-${{ github.event.number }}/*/index.html dist/preview-pages/pr-${{ github.event.number }}/storybooks/*/iframe.html; do
87+
echo "Adding skyux-icons.svg to $idx"
88+
sed -i'' 's~</head>~<link rel="prefetch" href="./skyux-icons.svg" class="skyux-icons-preview"></head>~' $idx
89+
cp -v ../skyux-icons/dist/assets/svg/skyux-icons.svg $(dirname $idx)/
90+
done
91+
working-directory: 'skyux'
92+
- name: Create Stackblitz link
93+
run: |
94+
mkdir -pv ${{ runner.temp }}/stackblitz
95+
cd ${{ runner.temp }}/stackblitz
96+
node ${{ github.workspace }}/skyux-icons/scripts/create-stackblitz-link.mjs --url="https://${{ github.repository_owner }}.github.io/skyux-icons/pr-${{ github.event.number }}/playground"
97+
mkdir -pv ${{ github.workspace }}/skyux/dist/preview-pages/pr-${{ github.event.number }}/stackblitz
98+
cp -v stackblitz.html ${{ github.workspace }}/skyux/dist/preview-pages/pr-${{ github.event.number }}/stackblitz/index.html
99+
- name: Generate comment for PR ${{ github.event.number }}
100+
run: |
101+
npx nx g @skyux-sdk/e2e-schematics:pr-comment --pr=pr-${{ github.event.number }} \
102+
--url="https://${{ github.repository_owner }}.github.io/skyux-icons" \
103+
--repoUrl="https://github.com/${{ github.repository }}" \
104+
--apps="$(ls dist/preview-pages/pr-${{ github.event.number }} | fgrep -v storybooks | tr '\n' ,)" \
105+
--storybooks="$(ls dist/preview-pages/pr-${{ github.event.number }}/storybooks | tr '\n' ,)" \
106+
--skipCompositeStorybook
107+
mv -v dist/pr_index.html dist/preview-pages/pr-${{ github.event.number }}/index.html
108+
working-directory: 'skyux'
109+
- name: Save PR ${{ github.event.number }} Preview
110+
uses: actions/upload-artifact@v4
111+
with:
112+
name: pr-${{ github.event.number }}
113+
path: skyux/dist/preview-pages/pr-${{ github.event.number }}
114+
overwrite: 'true'
115+
retention-days: 30
116+
if-no-files-found: error
117+
- name: Setup Pages
118+
uses: actions/configure-pages@v5
67119
- name: Upload artifact
68120
uses: actions/upload-pages-artifact@v3
69121
with:
70-
path: './dist'
122+
path: skyux/dist/preview-pages
71123
- name: Deploy to GitHub Pages
72124
id: deployment
73125
uses: actions/deploy-pages@v4
126+
- name: Comment
127+
run: |
128+
COMMENT_ID=$(gh api -H "Accept: application/vnd.github-commitcomment.raw+json" -H "X-GitHub-Api-Version: 2022-11-28" repos/${{ github.repository }}/issues/${{ github.event.number }}/comments -q 'map(select(.body | contains("Component Storybooks:"))) | .[0].id // empty')
129+
if [ -n "$COMMENT_ID" ]; then
130+
echo "Updating existing comment $COMMENT_ID"
131+
gh api --method PATCH -H "Accept: application/vnd.github+json" -H "X-GitHub-Api-Version: 2022-11-28" repos/${{ github.repository }}/issues/comments/${COMMENT_ID} -F body=@skyux/dist/pr_comment.md
132+
else
133+
echo "Creating a new comment"
134+
gh pr comment ${{ github.event.number }} -R ${{ github.repository }} -F skyux/dist/pr_comment.md
135+
fi
136+
env:
137+
GH_TOKEN: '${{ secrets.GH_PERSONAL_ACCESS_TOKEN }}'

.github/workflows/release-please.yml

Lines changed: 46 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -7,9 +7,10 @@ on:
77
push:
88
branches:
99
- master
10+
- '[0-9]+.x.x'
1011

1112
env:
12-
PRERELEASE: 'false'
13+
RELEASE_PR_PREFIX: 'chore: release'
1314

1415
permissions:
1516
contents: write
@@ -19,17 +20,49 @@ jobs:
1920
release:
2021
runs-on: ubuntu-latest
2122
steps:
22-
- uses: google-github-actions/release-please-action@v3
23-
id: release
23+
- uses: actions/checkout@v5
2424
with:
25-
changelog-types: '[{"type":"feat","section":"Features","hidden":false},{"type":"fix","section":"Bug Fixes","hidden":false},{"type":"deprecation","section":"Deprecations","hidden":false},{"type":"revert","section":"Reverts","hidden":false}]'
26-
release-type: 'node'
27-
default-branch: '${{ github.ref_name }}'
28-
package-name: '@skyux/icons'
29-
pull-request-title-pattern: 'chore: release ${version}'
30-
labels: 'autorelease ${{ github.ref_name }}: pending'
31-
release-labels: 'autorelease ${{ github.ref_name }}: tagged'
32-
prerelease: ${{ env.PRERELEASE == 'true' }}
33-
draft-pull-request: true
34-
include-v-in-tag: false
25+
fetch-depth: 0
3526
token: '${{ secrets.GH_PERSONAL_ACCESS_TOKEN }}'
27+
- uses: actions/setup-node@v5
28+
with:
29+
cache: 'npm'
30+
node-version-file: '.nvmrc'
31+
- name: npm install
32+
run: npm ci
33+
- name: Next release
34+
if: ${{ github.event_name != 'push' || ! startsWith(github.event.head_commit.message, env.RELEASE_PR_PREFIX) }}
35+
# Create or update a release branch and its pull request.
36+
run: npx skyux-dev release ${{ github.event_name == 'workflow_dispatch' && ! endsWith(github.event.ref, 'main') && ! endsWith(github.event.ref, '.x.x') && '--dry-run=true' || '' }}
37+
env:
38+
GH_TOKEN: ${{ secrets.GH_PERSONAL_ACCESS_TOKEN }}
39+
- uses: actions/github-script@v8
40+
name: Release
41+
if: ${{ github.event_name == 'push' && startsWith(github.event.head_commit.message, env.RELEASE_PR_PREFIX) }}
42+
id: release
43+
# Create a release based on the release pull request.
44+
with:
45+
github-token: ${{ secrets.GH_PERSONAL_ACCESS_TOKEN }}
46+
script: |
47+
const prevVersion = JSON.parse((await exec.getExecOutput('git', ['cat-file', '--textconv', `${context.payload.before}:package.json`])).stdout).version;
48+
const nextVersion = JSON.parse((await exec.getExecOutput('git', ['cat-file', '--textconv', `${context.payload.after}:package.json`])).stdout).version;
49+
if (!nextVersion || prevVersion === nextVersion) {
50+
console.log('No version change detected. Exiting.');
51+
process.exit(0);
52+
}
53+
core.setOutput('release_created', '1');
54+
core.setOutput('tag_name', nextVersion);
55+
56+
const releaseExists = await github.rest.repos.getReleaseByTag({ ...context.repo, tag: nextVersion }).then(() => true).catch(() => false);
57+
if (!releaseExists) {
58+
const releaseNotes = (await exec.getExecOutput('npx', ['skyux-dev', 'release-notes', `--releaseName=${nextVersion}`])).stdout;
59+
await github.rest.repos.createRelease({ ...context.repo, name: `v${nextVersion}`, tag_name: nextVersion, body: releaseNotes, prerelease: nextVersion.includes('-') });
60+
}
61+
- name: Notify Slack
62+
if: ${{ steps.release.outputs.release_created }}
63+
uses: rtCamp/action-slack-notify@07cbdbfd6c6190970778d8f98f11d073b2932aae # v2.3.3
64+
env:
65+
SLACK_WEBHOOK: ${{ secrets.SLACK_WEBHOOK }}
66+
SLACK_MESSAGE: Successfully published SKY UX Icons ${{ steps.release.outputs.tag_name }} to NPM. http://github.com/${{ github.repository }}/blob/${{ github.ref_name }}/CHANGELOG.md
67+
SLACK_ICON: https://github.com/blackbaud.png?size=48
68+
SLACK_USERNAME: SKY UX

.nvmrc

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1 +1 @@
1-
20.11.1
1+
20.19.5

.skyuxdev.json

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,4 @@
11
{
2-
"baseBranch": "master"
2+
"baseBranch": "master",
3+
"releaseBranch": "release-please--branches--{baseBranch}--components--icons"
34
}

.versionrc

Lines changed: 33 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,33 @@
1+
{
2+
"//": "Configuration for https://github.com/absolute-version/commit-and-tag-version",
3+
"releaseAs": null,
4+
"prerelease": null,
5+
"preset": "angular",
6+
"header": "# Changelog\n\n",
7+
"releaseCommitMessageFormat": "chore: release {{currentTag}}",
8+
"scripts": {
9+
"prebump": "npx skyux-dev release-version"
10+
},
11+
"skip": {
12+
"tag": true
13+
},
14+
"tagPrefix": "",
15+
"types": [
16+
{
17+
"type": "feat",
18+
"section": "Features"
19+
},
20+
{
21+
"type": "fix",
22+
"section": "Bug Fixes"
23+
},
24+
{
25+
"type": "deprecation",
26+
"section": "Deprecations"
27+
},
28+
{
29+
"type": "revert",
30+
"section": "Reverts"
31+
}
32+
]
33+
}

0 commit comments

Comments
 (0)