Skip to content
Draft
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
2 changes: 1 addition & 1 deletion .github/copilot-instructions.md
Original file line number Diff line number Diff line change
Expand Up @@ -52,7 +52,7 @@ Always reference these instructions first and fallback to search or bash command
# Timeout: Use 60 seconds

# E2E tests require Cypress download - may not work in restricted environments
# If available: pnpm test (takes variable time depending on tests)
# If available: pnpm test:e2e (takes variable time depending on tests)
```

4. **Run Development Servers**:
Expand Down
24 changes: 24 additions & 0 deletions .github/workflows/check-backend.yaml
Original file line number Diff line number Diff line change
@@ -0,0 +1,24 @@
name: LintBackend

on: [workflow_call]

permissions: read-all

jobs:
check-backend:
runs-on: ubuntu-latest
env:
BACKEND_DIR: ./backend
steps:
- uses: actions/checkout@v4
- uses: ./.github/actions/uv-python-install
name: Install Python, uv and Python dependencies
with:
extra-dependencies: --extra tests --extra mypy --extra custom-data
working-directory: ${{ env.BACKEND_DIR }}
- name: Lint backend
run: uv run scripts/lint.py
- name: Check backend formatting
run: uv run scripts/format.py --check
- name: Typecheck backend
run: uv run scripts/type-check.py
19 changes: 19 additions & 0 deletions .github/workflows/check-frontend.yaml
Original file line number Diff line number Diff line change
@@ -0,0 +1,19 @@
name: Lint frontend & libs

on: [workflow_call]

permissions: read-all

jobs:
check-frontend:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v4
- uses: ./.github/actions/pnpm-node-install
name: Install Node, pnpm and dependencies.
- name: Lint frontend & libs
run: pnpm lint
- name: Check frontend & libs formatting
run: pnpm format
- name: Typecheck frontend & libs
run: pnpm type-check
16 changes: 8 additions & 8 deletions .github/workflows/ci.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -18,23 +18,23 @@ on:
permissions: read-all

jobs:
pytest:
uses: ./.github/workflows/pytest.yaml
check-backend:
uses: ./.github/workflows/check-backend.yaml
secrets: inherit
lint-backend:
uses: ./.github/workflows/lint-backend.yaml
check-frontend:
uses: ./.github/workflows/check-frontend.yaml
secrets: inherit
tests:
uses: ./.github/workflows/tests.yaml
secrets: inherit
e2e-tests:
uses: ./.github/workflows/e2e-tests.yaml
secrets: inherit
lint-ui:
uses: ./.github/workflows/lint-ui.yaml
secrets: inherit
ci:
runs-on: ubuntu-latest
name: Run CI
if: always() # This ensures the job always runs
needs: [lint-backend, pytest, lint-ui, e2e-tests]
needs: [check-backend, check-frontend, tests, e2e-tests]
steps:
# Propagate failure
- name: Check dependent jobs
Expand Down
4 changes: 2 additions & 2 deletions .github/workflows/e2e-tests.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,7 @@ on: [workflow_call]
permissions: read-all

jobs:
ci:
e2e-tests:
runs-on: ${{ matrix.os }}
strategy:
matrix:
Expand All @@ -31,7 +31,7 @@ jobs:
- name: Run tests
env:
CYPRESS_RECORD_KEY: ${{ secrets.CYPRESS_RECORD_KEY }}
run: pnpm test
run: pnpm test:e2e
shell: bash
- name: Upload screenshots
uses: actions/upload-artifact@v4
Expand Down
32 changes: 0 additions & 32 deletions .github/workflows/lint-backend.yaml

This file was deleted.

17 changes: 0 additions & 17 deletions .github/workflows/lint-ui.yaml

This file was deleted.

11 changes: 4 additions & 7 deletions .github/workflows/pytest.yaml → .github/workflows/tests.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,7 @@ on: [workflow_call]
permissions: read-all

jobs:
pytest:
tests:
runs-on: ubuntu-latest
strategy:
matrix:
Expand All @@ -21,10 +21,7 @@ jobs:
with:
python-version: ${{ matrix.python-version }}
extra-dependencies: --extra tests --extra mypy --extra custom-data
working-directory: ${{ env.BACKEND_DIR }}
- name: Build UI components
run: pnpm run buildUi
timeout-minutes: 5
- name: Run Pytest
- name: Run backend tests
run: uv run --no-project pytest --cov=chainlit/
working-directory: ${{ env.BACKEND_DIR }}
- name: Run frontend tests
run: pnpm run test
3 changes: 1 addition & 2 deletions .gitignore
Original file line number Diff line number Diff line change
Expand Up @@ -59,7 +59,6 @@ dist-ssr
.aider*
.coverage

backend/README.md
backend/.dmypy.json
.dmypy.json

.history
36 changes: 17 additions & 19 deletions CONTRIBUTING.md
Original file line number Diff line number Diff line change
Expand Up @@ -15,13 +15,12 @@ I've copy/pasted the whole document there, and then formatted it with prettier.
- [Requirements](#requirements)
- [Set up the repo](#set-up-the-repo)
- [Install dependencies](#install-dependencies)
- [Build Frontend](#build-frontend)
- [Start the Chainlit server from source](#start-the-chainlit-server-from-source)
- [Start the UI from source](#start-the-ui-from-source)
- [Run the tests](#run-the-tests)
- [Backend unit tests](#backend-unit-tests)
- [Frontend unit tests](#frontend-unit-tests)
- [E2E tests](#e2e-tests)
- [Headed/debugging](#headeddebugging)

## Local setup

Expand Down Expand Up @@ -116,6 +115,14 @@ cd backend
uv run pytest --cov=chainlit
```

### Frontend unit tests

This will run the frontend's unit tests.

```
pnpm test
```

### E2E tests

You may need additional configuration or dependency installation to run Cypress. See the [Cypress system requirements](https://docs.cypress.io/app/get-started/install-cypress#System-requirements) for details.
Expand All @@ -124,31 +131,22 @@ This will run end to end tests, assessing both the frontend, the backend and the

```sh
// from root
pnpm test // will do cypress run
pnpm test -- --spec cypress/e2e/copilot // will run single test with the name copilot
pnpm test -- --spec "cypress/e2e/copilot,cypress/e2e/data_layer" // will run two tests with the names copilot and data_layer
pnpm test -- --spec "cypress/e2e/**/async-*" // will run all async tests
pnpm test -- --spec "cypress/e2e/**/sync-*" // will run all sync tests
pnpm test -- --spec "cypress/e2e/**/spec.cy.ts" // will run all usual tests
pnpm test:e2e // will do cypress run
pnpm test:e2e -- --spec cypress/e2e/copilot // will run single test with the name copilot
pnpm test:e2e -- --spec "cypress/e2e/copilot,cypress/e2e/data_layer" // will run two tests with the names copilot and data_layer
pnpm test:e2e -- --spec "cypress/e2e/**/async-*" // will run all async tests
pnpm test:e2e -- --spec "cypress/e2e/**/sync-*" // will run all sync tests
pnpm test:e2e -- --spec "cypress/e2e/**/spec.cy.ts" // will run all usual tests
```

(Go grab a cup of something, this will take a while.)

For debugging purposes, you can use the **interactive mode** (Cypress UI). Run:

```
pnpm test:interactive // runs `cypress open`
pnpm test:e2e:interactive // runs `cypress open`
```

Once you create a pull request, the tests will automatically run. It is a good practice to run the tests locally before pushing.

Make sure to run `uv sync` again whenever you've updated the frontend!

### Headed/debugging

Causes the Electron browser to be shown on screen and keeps it open after tests are done.
Extremely useful for debugging!

```sh
SINGLE_TEST=password_auth CYPRESS_OPTIONS='--headed --no-exit' pnpm test
```
Make sure to run `uv sync` again whenever you've updated the frontend!
2 changes: 1 addition & 1 deletion backend/build.py
Original file line number Diff line number Diff line change
Expand Up @@ -32,7 +32,7 @@ def pnpm_install(project_root: pathlib.Path, pnpm_path: str):


def pnpm_buildui(project_root: pathlib.Path, pnpm_path: str):
run_subprocess([pnpm_path, "buildUi"], project_root)
run_subprocess([pnpm_path, "build"], project_root)


def copy_directory(src: pathlib.Path, dst: pathlib.Path, description: str):
Expand Down
4 changes: 2 additions & 2 deletions backend/pyproject.toml
Original file line number Diff line number Diff line change
Expand Up @@ -87,7 +87,7 @@ tests = [
"moto>=5.0.14,<6.0.0",
]
dev = [
"ruff>=0.9.0,<1.0.0",
"ruff>=0.13.3,<1.0.0",
]
mypy = [
"mypy>=1.13,<2.0.0",
Expand Down Expand Up @@ -164,7 +164,7 @@ testpaths = ["tests"]
asyncio_mode = "auto"

[tool.ruff]
target-version = "py39"
target-version = "py310"

[tool.ruff.lint]
select = [
Expand Down
8 changes: 4 additions & 4 deletions frontend/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -7,10 +7,10 @@
"dev": "vite",
"build": "vite build",
"preview": "vite preview",
"lint": "eslint ./src --ext .ts,.tsx && tsc --noemit",
"format": "prettier 'src/**/*.{ts,tsx,css}' --write",
"test": "vitest run",
"prepublishOnly": "pnpm run build && pnpm test"
"lint": "eslint ./src --ext .ts,.tsx",
"format": "prettier 'src/**/*.{ts,tsx,css}'",
"type-check": "tsc --noemit",
"test": "vitest run"
},
"dependencies": {
"@chainlit/react-client": "workspace:^",
Expand Down
4 changes: 3 additions & 1 deletion libs/copilot/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -8,7 +8,9 @@
"build": "vite build",
"preview": "vite preview",
"lint": "eslint ./src --ext .ts,.tsx",
"format": "prettier 'src/**/*.{ts,tsx}' --write",
"format": "prettier 'src/**/*.{ts,tsx}'",
"type-check": "tsc --noemit",
"test": "echo no tests yet",
"storybook": "storybook dev -p 6006",
"build-storybook": "storybook build"
},
Expand Down
8 changes: 5 additions & 3 deletions libs/react-client/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -3,10 +3,12 @@
"description": "Websocket client to connect to your chainlit app.",
"version": "0.3.0",
"scripts": {
"build": "tsup src/index.ts --tsconfig tsconfig.build.json --clean --format esm,cjs --dts --external react --external recoil --minify --sourcemap --treeshake",
"preinstall": "npx only-allow pnpm",
"dev": "tsup src/index.ts --clean --format esm,cjs --dts --external react --external recoil --minify --sourcemap --treeshake",
"lint": "eslint ./src --ext ts,tsx --report-unused-disable-directives --max-warnings 0 && tsc --noemit",
"format": "prettier '**/*.{ts,tsx}' --write",
"build": "tsup src/index.ts --tsconfig tsconfig.build.json --clean --format esm,cjs --dts --external react --external recoil --minify --sourcemap --treeshake",
"lint": "eslint ./src --ext ts,tsx --report-unused-disable-directives --max-warnings 0",
"format": "prettier '**/*.{ts,tsx}'",
"type-check": "tsc --noemit",
"test": "echo no tests yet"
},
"repository": {
Expand Down
10 changes: 5 additions & 5 deletions lint-staged.config.js
Original file line number Diff line number Diff line change
@@ -1,11 +1,11 @@
// eslint-disable-next-line no-undef
module.exports = {
'**/*.{js,jsx,ts,tsx}': ['npx prettier --write', 'npx eslint --fix'],
'**/*.{ts,tsx}': [() => 'tsc --skipLibCheck --noEmit'],
'**/*.{js,jsx,ts,tsx}': ['pnpm lint --fix', 'pnpm format --fix'],
'**/*.{ts,tsx}': [() => 'pnpm type-check'],
'**/*.py': [
'uv run --project backend ruff check --fix',
'uv run --project backend ruff format',
() => 'pnpm run lintPython'
'uv run scripts/lint.py',
'uv run scripts/format.py --check',
'uv run scripts/type_check.py',
],
'.github/workflows/**': ['actionlint']
};
17 changes: 7 additions & 10 deletions package.json
Original file line number Diff line number Diff line change
Expand Up @@ -19,17 +19,14 @@
},
"scripts": {
"preinstall": "npx only-allow pnpm",
"test": "cypress run",
"test:interactive": "cypress open",
"test:ui": "cd frontend && pnpm test",
"prepare": "husky",
"lint": "pnpm run lintUi && pnpm run lintPython",
"lintUi": "pnpm run --parallel lint",
"formatUi": "pnpm run --parallel format",
"lintPython": "cd backend && uv run dmypy run -- chainlit/ tests/",
"formatPython": "black `git ls-files | grep '.py$'` && isort --profile=black .",
"build:libs": "cd libs/react-client && pnpm run build && cd ../copilot && pnpm run build",
"buildUi": "pnpm build:libs && cd frontend && pnpm run build"
"build": "pnpm run --recursive build",
"lint": "pnpm run --parallel lint",
"format": "pnpm run --parallel format",
"type-check": "pnpm run --parallel type-check",
"test": "pnpm run --recursive test",
"test:e2e": "cypress run",
"test:e2e:interactive": "cypress open"
},
"pnpm": {
"overrides": {
Expand Down
12 changes: 12 additions & 0 deletions pyproject.toml
Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
[dependency-groups]
backend = ["chainlit"]

[tool.uv]
default-groups = ["backend"]
package = false

[tool.uv.sources]
chainlit = { workspace = true }

[tool.uv.workspace]
members = ["backend"]
Loading
Loading