Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
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
144 changes: 127 additions & 17 deletions .github/workflows/ci.yml
Original file line number Diff line number Diff line change
@@ -1,12 +1,18 @@
name: CI

on:
push:
branches:
- core
- basic
pull_request:
branches:
- core
- basic

env:
NODE_VERSION: "22.x"

jobs:
lint-tests:
uses: ./.github/workflows/run-tests.yml
Expand All @@ -15,26 +21,81 @@ jobs:
test-command: pnpm lint

unit-tests:
uses: ./.github/workflows/run-tests.yml
with:
test-type: unit
test-command: pnpm test:ci
runs-on: ubuntu-latest

# For every direct push to target branches or when it's active PR
if: ${{ github.event_name == 'push' || !github.event.pull_request.draft }}
steps:
- name: Checkout
uses: actions/checkout@v4

- name: Enable corepack
run: corepack enable

- name: Setup Node.js
uses: actions/setup-node@v4
with:
node-version: ${{ env.NODE_VERSION }}
cache: "pnpm"

- name: Get pnpm store directory
id: pnpm-cache
shell: bash
run: |
echo "STORE_PATH=$(pnpm store path)" >> $GITHUB_OUTPUT

- name: Setup pnpm cache
uses: actions/cache@v4
with:
path: ${{ steps.pnpm-cache.outputs.STORE_PATH }}
key: ${{ runner.os }}-pnpm-store-${{ hashFiles('**/pnpm-lock.yaml') }}
restore-keys: |
${{ runner.os }}-pnpm-store-

- name: Install dependencies
run: pnpm install --no-frozen-lockfile --ignore-scripts

- name: Run coverage
run: pnpm test:coverage

- name: Run unit tests
run: pnpm test:ci

- name: Upload test results
if: success() || failure()
uses: actions/upload-artifact@v4
with:
name: unit-test-results
path: reports/**/*

- name: Upload coverage report
if: success() || failure()
uses: actions/upload-artifact@v4
with:
name: unit-coverage-report
path: coverage/**/*

storybook-tests:
runs-on: ubuntu-latest
env:
STORYBOOK_DISABLE_TELEMETRY: 1
STORYBOOK: "true"
CI: true

# For every direct push to target branches or when it's active PR
if: ${{ github.event_name == 'push' || !github.event.pull_request.draft }}
steps:
- name: Checkout
uses: actions/checkout@v4

- name: Enable corepack
run: corepack enable

# https://github.com/storybookjs/test-runner/issues/301
# - name: Install Node.js
# uses: actions/setup-node@v3
# with:
# node-version: "16.x"
# cache: "pnpm"
- name: Setup Node.js
uses: actions/setup-node@v4
with:
node-version: ${{ env.NODE_VERSION }}
cache: "pnpm"

- name: Get pnpm store directory
id: pnpm-cache
Expand All @@ -53,8 +114,8 @@ jobs:
- name: Install dependencies
run: pnpm install --no-frozen-lockfile --ignore-scripts

- name: Install Playwright
run: pnpm exec playwright install --with-deps
- name: Install Playwright browsers
run: pnpm exec playwright install chromium --with-deps --only-shell

- name: Build Storybook
run: pnpm build-storybook --quiet
Expand All @@ -63,13 +124,21 @@ jobs:
run: |
pnpm exec concurrently -k -s first -n "SB,TEST" -c "magenta,blue" \
"pnpm exec http-server storybook-static --port 6006 --silent" \
"pnpm exec wait-on tcp:127.0.0.1:6006 && pnpm exec test-storybook --json --outputFile storybook-report.json a"
"pnpm exec wait-on tcp:6006 && pnpm exec test-storybook --coverage --coverageDirectory=coverage --excludeTags=\"!test\" --junit --outputFile reports/storybook-report.json"

- name: Upload json report artifacts
- name: Upload test results
if: success() || failure()
uses: actions/upload-artifact@v4
with:
name: storybook-report
path: storybook-report.json
name: storybook-test-results
path: reports/**/*

- name: Upload coverage report
if: success() || failure()
uses: actions/upload-artifact@v4
with:
name: storybook-coverage-report
path: coverage/**/*

build:
needs: [lint-tests, unit-tests, storybook-tests]
Expand Down Expand Up @@ -117,8 +186,49 @@ jobs:
name: build
path: dist

test-reports:
needs: [unit-tests, storybook-tests]
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v4

- name: Download Artifacts
uses: actions/download-artifact@v4

- name: Generate Full Coverage Report
uses: danielpalme/ReportGenerator-GitHub-Action@v5
with:
reports: "unit-coverage-report/lcov.info;storybook-coverage-report/lcov.info"
reporttypes: "MarkdownSummaryGithub;JsonSummary;Html"
targetdir: coverage-report

- name: Add Coverage Report Comment to PR
if: github.event_name == 'pull_request'
run: gh pr comment $PR_NUMBER --body-file coverage-report/SummaryGithub.md
env:
GH_TOKEN: ${{ secrets.GITHUB_TOKEN }}
PR_NUMBER: ${{ github.event.number }}

- name: Publish Coverage Report in Build Summary
run: cat coverage-report/SummaryGithub.md >> $GITHUB_STEP_SUMMARY

- name: Upload Full Coverage Report
uses: actions/upload-artifact@v4
with:
name: full-coverage-report
path: coverage-report/**/*

- name: Publish Test Results
uses: dorny/test-reporter@v2
id: test-reporter
with:
name: Test Results
path: unit-test-results/**/*.xml,storybook-test-results/**/*.xml
reporter: jest-junit
fail-on-error: false

deploy:
needs: build
needs: [build, test-reports]
runs-on: ubuntu-latest
steps:
- name: Get build artifacts
Expand Down
16 changes: 16 additions & 0 deletions .storybook/main.ts
Original file line number Diff line number Diff line change
@@ -1,3 +1,4 @@
import type { AddonOptionsVite } from "@storybook/addon-coverage";
import type { StorybookConfig } from "@storybook/react-vite";
import * as tsconfigPaths from "vite-tsconfig-paths";

Expand All @@ -7,6 +8,15 @@ const config: StorybookConfig = {
addons: [
"@storybook/addon-links",
"@storybook/addon-a11y",
{
name: "@storybook/addon-coverage",
options: {
istanbul: {
include: ["src/**/*.tsx"],
exclude: ["src/**/*.ts", "src/test-lib/*.tsx"],
},
} satisfies AddonOptionsVite,
},
"@storybook/addon-docs",
],

Expand All @@ -28,6 +38,12 @@ const config: StorybookConfig = {
typescript: {
reactDocgen: "react-docgen-typescript",
},

build: {
test: {
disabledAddons: ["@storybook/addon-docs"],
},
},
};

export default config;
21 changes: 12 additions & 9 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -24,7 +24,7 @@ This version is free of any libraries. If the `core` version doesn't match your
- TypeScript support.
- [Devcontainer](https://code.visualstudio.com/docs/devcontainers/containers) config for VS Code.
- [PNPM](https://pnpm.io/) as a package manager.
- CI setup (automate tests, build, deploy draft) with [GitHub Actions](https://docs.github.com/en/actions).
- CI setup (tests, build, tests coverage report, deploy draft) with [GitHub Actions](https://docs.github.com/en/actions).
- [Github Copilot](https://github.com/features/copilot) instructions configured for efficient chat and agent usage.

## Extended version - `core`
Expand Down Expand Up @@ -91,14 +91,17 @@ Learn more about using this template in practice below.

## Basic commands

| Command | Description |
| ---------------------- | ---------------------------------------------------------------------------------------------------------------------------------------------------------- |
| `pnpm dev` | Runs dev server with the HMR locally on port `5173` |
| `pnpm build` | Builds optimized app package |
| `pnpm test` | Runs unit tests |
| `pnpm storybook` | Runs a Storybook locally on port `6006` |
| `pnpm test-storybook` | Runs integration tests (requires a running Storybook on port `6006` - more info [here](https://storybook.js.org/blog/interaction-testing-with-storybook/)) |
| `pnpm build-storybook` | Builds static app with [a Storybook's content](https://storybook.js.org/docs/react/sharing/publish-storybook) |
| Command | Description |
| ------------------------------ | ---------------------------------------------------------------------------------------------------------------------------------------------------------- |
| `pnpm dev` | Runs dev server with the HMR locally on port `5173` |
| `pnpm lint` | Checks for lint errors |
| `pnpm build` | Builds optimized app package |
| `pnpm test` | Runs unit tests |
| `pnpm test:coverage` | Runs unit tests with coverage |
| `pnpm storybook` | Runs a Storybook locally on port `6006` |
| `pnpm test-storybook` | Runs integration tests (requires a running Storybook on port `6006` - more info [here](https://storybook.js.org/blog/interaction-testing-with-storybook/)) |
| `pnpm test-storybook:coverage` | Runs integration tests with coverage |
| `pnpm build-storybook` | Builds static app with [a Storybook's content](https://storybook.js.org/docs/react/sharing/publish-storybook) |

# Contributing

Expand Down
5 changes: 4 additions & 1 deletion package.json
Original file line number Diff line number Diff line change
Expand Up @@ -7,12 +7,14 @@
"dev": "vite",
"build": "tsc && vite build",
"test": "vitest",
"test:ci": "vitest run --reporter verbose --reporter=junit --outputFile=./unit-report.xml",
"test:ci": "vitest run --reporter verbose --reporter=junit --outputFile=./reports/unit-report.xml --coverage --coverage.reporter=lcov --coverage.reportsDirectory=./coverage",
"test:coverage": "vitest run --coverage",
"preview": "vite preview",
"lint": "CI=true eslint . --ext ts,tsx --ignore-pattern '*.d.ts' --report-unused-disable-directives --max-warnings 0",
"prepare": "husky install",
"storybook": "storybook dev -p 6006",
"test-storybook": "test-storybook --watch",
"test-storybook:coverage": "test-storybook --coverage",
"build-storybook": "storybook build"
},
"dependencies": {
Expand All @@ -23,6 +25,7 @@
"devDependencies": {
"@eslint/js": "9.24.0",
"@storybook/addon-a11y": "9.0.15",
"@storybook/addon-coverage": "2.0.0",
"@storybook/addon-docs": "9.0.15",
"@storybook/addon-links": "9.0.15",
"@storybook/react-vite": "9.0.15",
Expand Down
Loading
Loading