mirror of
https://github.com/zitadel/zitadel.git
synced 2025-08-11 20:07:32 +00:00
standalone to use the latest version of packs
This commit is contained in:
11
login/apps/login/.eslintrc.cjs
Executable file → Normal file
11
login/apps/login/.eslintrc.cjs
Executable file → Normal file
@@ -1,12 +1,7 @@
|
|||||||
module.exports = {
|
module.exports = {
|
||||||
extends: ["next/core-web-vitals"],
|
extends: ["next/core-web-vitals"],
|
||||||
ignorePatterns: ["external/**/*.ts"],
|
|
||||||
rules: {
|
rules: {
|
||||||
"@next/next/no-html-link-for-pages": "off",
|
"@next/next/no-img-element": "off",
|
||||||
},
|
"react/no-unescaped-entities": "off"
|
||||||
settings: {
|
}
|
||||||
react: {
|
|
||||||
version: "detect",
|
|
||||||
},
|
|
||||||
},
|
|
||||||
};
|
};
|
||||||
|
58
login/apps/login/.github/workflows/ci.yml
vendored
58
login/apps/login/.github/workflows/ci.yml
vendored
@@ -1,58 +0,0 @@
|
|||||||
name: CI
|
|
||||||
|
|
||||||
on:
|
|
||||||
push:
|
|
||||||
branches: [ main ]
|
|
||||||
pull_request:
|
|
||||||
branches: [ main ]
|
|
||||||
|
|
||||||
jobs:
|
|
||||||
test:
|
|
||||||
runs-on: ubuntu-latest
|
|
||||||
|
|
||||||
strategy:
|
|
||||||
matrix:
|
|
||||||
node-version: [18.x, 20.x]
|
|
||||||
|
|
||||||
steps:
|
|
||||||
- uses: actions/checkout@v4
|
|
||||||
|
|
||||||
- name: Use Node.js ${{ matrix.node-version }}
|
|
||||||
uses: actions/setup-node@v4
|
|
||||||
with:
|
|
||||||
node-version: ${{ matrix.node-version }}
|
|
||||||
cache: 'npm'
|
|
||||||
|
|
||||||
- name: Prepare standalone
|
|
||||||
run: ./prepare-standalone.sh
|
|
||||||
|
|
||||||
- name: Run tests
|
|
||||||
run: npm run test:unit
|
|
||||||
|
|
||||||
- name: Run linting
|
|
||||||
run: npm run lint
|
|
||||||
|
|
||||||
- name: Build application
|
|
||||||
run: npm run build:standalone
|
|
||||||
|
|
||||||
build-docker:
|
|
||||||
needs: test
|
|
||||||
runs-on: ubuntu-latest
|
|
||||||
if: github.ref == 'refs/heads/main'
|
|
||||||
|
|
||||||
steps:
|
|
||||||
- uses: actions/checkout@v4
|
|
||||||
|
|
||||||
- name: Prepare standalone
|
|
||||||
run: ./prepare-standalone.sh
|
|
||||||
|
|
||||||
- name: Build Docker image
|
|
||||||
run: |
|
|
||||||
docker build -t zitadel-login-ui .
|
|
||||||
|
|
||||||
- name: Test Docker image
|
|
||||||
run: |
|
|
||||||
docker run --rm -d -p 3000:3000 --name test-container zitadel-login-ui
|
|
||||||
sleep 10
|
|
||||||
curl -f http://localhost:3000 || exit 1
|
|
||||||
docker stop test-container
|
|
7
login/apps/login/.gitignore
vendored
7
login/apps/login/.gitignore
vendored
@@ -1,3 +1,10 @@
|
|||||||
custom-config.js
|
custom-config.js
|
||||||
.env*.local
|
.env*.local
|
||||||
standalone
|
standalone
|
||||||
|
|
||||||
|
# Generated standalone files (temporary)
|
||||||
|
*.generated.*
|
||||||
|
package.monorepo.backup.json
|
||||||
|
|
||||||
|
# TypeScript build info
|
||||||
|
tsconfig.tsbuildinfo
|
||||||
|
@@ -1,54 +0,0 @@
|
|||||||
# Dependencies
|
|
||||||
/node_modules
|
|
||||||
/.pnp
|
|
||||||
.pnp.js
|
|
||||||
|
|
||||||
# Testing
|
|
||||||
/coverage
|
|
||||||
|
|
||||||
# Next.js
|
|
||||||
/.next/
|
|
||||||
/out/
|
|
||||||
|
|
||||||
# Production
|
|
||||||
/build
|
|
||||||
|
|
||||||
# Misc
|
|
||||||
.DS_Store
|
|
||||||
*.pem
|
|
||||||
|
|
||||||
# Debug
|
|
||||||
npm-debug.log*
|
|
||||||
yarn-debug.log*
|
|
||||||
yarn-error.log*
|
|
||||||
|
|
||||||
# Local env files
|
|
||||||
.env*.local
|
|
||||||
|
|
||||||
# Vercel
|
|
||||||
.vercel
|
|
||||||
|
|
||||||
# TypeScript
|
|
||||||
*.tsbuildinfo
|
|
||||||
next-env.d.ts
|
|
||||||
|
|
||||||
# Turbo
|
|
||||||
.turbo
|
|
||||||
|
|
||||||
# IDE
|
|
||||||
.vscode/
|
|
||||||
.idea/
|
|
||||||
|
|
||||||
# Logs
|
|
||||||
logs
|
|
||||||
*.log
|
|
||||||
|
|
||||||
# Optional npm cache directory
|
|
||||||
.npm
|
|
||||||
|
|
||||||
# Optional eslint cache
|
|
||||||
.eslintcache
|
|
||||||
|
|
||||||
# Package manager locks (we use npm in standalone)
|
|
||||||
pnpm-lock.yaml
|
|
||||||
yarn.lock
|
|
@@ -12,11 +12,20 @@ This is the standalone version of the ZITADEL Login UI, a Next.js application th
|
|||||||
### Setup
|
### Setup
|
||||||
|
|
||||||
1. **Prepare the standalone environment:**
|
1. **Prepare the standalone environment:**
|
||||||
|
|
||||||
```bash
|
```bash
|
||||||
./prepare-standalone.sh
|
./prepare-standalone.sh --install
|
||||||
|
```
|
||||||
|
|
||||||
|
Or for manual control:
|
||||||
|
|
||||||
|
```bash
|
||||||
|
./prepare-standalone.sh --no-install
|
||||||
|
npm install
|
||||||
```
|
```
|
||||||
|
|
||||||
2. **Start development server:**
|
2. **Start development server:**
|
||||||
|
|
||||||
```bash
|
```bash
|
||||||
npm run dev
|
npm run dev
|
||||||
```
|
```
|
||||||
@@ -48,14 +57,46 @@ ZITADEL_API_URL=https://your-zitadel-instance.com
|
|||||||
# Add other required environment variables
|
# Add other required environment variables
|
||||||
```
|
```
|
||||||
|
|
||||||
|
### Package Management
|
||||||
|
|
||||||
|
This standalone version automatically uses the latest published versions of:
|
||||||
|
|
||||||
|
- `@zitadel/client` - ZITADEL client library (latest)
|
||||||
|
- `@zitadel/proto` - ZITADEL protocol definitions (latest)
|
||||||
|
|
||||||
|
To update to the latest versions, simply run:
|
||||||
|
|
||||||
|
```bash
|
||||||
|
npm update @zitadel/client @zitadel/proto
|
||||||
|
```
|
||||||
|
|
||||||
## Differences from Monorepo Version
|
## Differences from Monorepo Version
|
||||||
|
|
||||||
This standalone version includes:
|
This standalone version includes:
|
||||||
|
|
||||||
- Self-contained configuration files
|
- **Published packages**: Uses latest published versions of `@zitadel/client` and `@zitadel/proto`
|
||||||
- Published versions of `@zitadel/client` and `@zitadel/proto` packages
|
- **Self-contained configuration**: All configuration files are standalone-ready
|
||||||
- Standalone build scripts
|
- **Simplified dependencies**: Removes monorepo-specific devDependencies and tooling
|
||||||
- Independent dependency management
|
- **Streamlined build scripts**: Optimized scripts for standalone development
|
||||||
|
- **Independent dependency management**: No workspace or turbo dependencies
|
||||||
|
|
||||||
|
## Architecture
|
||||||
|
|
||||||
|
### Dual-Mode Design
|
||||||
|
|
||||||
|
This project supports both monorepo and standalone modes:
|
||||||
|
|
||||||
|
- **Monorepo mode**: Uses `workspace:*` dependencies for local development
|
||||||
|
- **Standalone mode**: Uses published npm packages for distribution
|
||||||
|
|
||||||
|
### Automatic Conversion
|
||||||
|
|
||||||
|
The conversion between modes is handled by intelligent scripts:
|
||||||
|
|
||||||
|
1. **`prepare-standalone.sh`**: Main conversion script for end users
|
||||||
|
2. **`scripts/prepare-standalone.js`**: Advanced preparation with latest package versions
|
||||||
|
3. **`scripts/build-standalone.js`**: Generates standalone configs without modifying current setup
|
||||||
|
4. **`scripts/config-manager.js`**: Switches between monorepo and standalone configurations
|
||||||
|
|
||||||
## Contributing
|
## Contributing
|
||||||
|
|
||||||
@@ -71,6 +112,7 @@ When contributing to this standalone version:
|
|||||||
This repository is maintained as a Git subtree of the main ZITADEL repository.
|
This repository is maintained as a Git subtree of the main ZITADEL repository.
|
||||||
|
|
||||||
To sync changes from the main repo:
|
To sync changes from the main repo:
|
||||||
|
|
||||||
```bash
|
```bash
|
||||||
# In the main ZITADEL repo
|
# In the main ZITADEL repo
|
||||||
git subtree push --prefix=login/apps/login origin typescript-login-standalone
|
git subtree push --prefix=login/apps/login origin typescript-login-standalone
|
||||||
|
@@ -14,7 +14,8 @@
|
|||||||
"build:login:standalone": "NEXT_PUBLIC_BASE_PATH=/ui/v2/login NEXT_OUTPUT_MODE=standalone pnpm build",
|
"build:login:standalone": "NEXT_PUBLIC_BASE_PATH=/ui/v2/login NEXT_OUTPUT_MODE=standalone pnpm build",
|
||||||
"start": "pnpm build && pnpm exec next start",
|
"start": "pnpm build && pnpm exec next start",
|
||||||
"start:built": "pnpm exec next start",
|
"start:built": "pnpm exec next start",
|
||||||
"clean": "pnpm mock:stop && rm -rf .turbo && rm -rf node_modules && rm -rf .next"
|
"clean": "pnpm mock:stop && rm -rf .turbo && rm -rf node_modules && rm -rf .next",
|
||||||
|
"standalone:prepare": "node scripts/prepare-standalone.js"
|
||||||
},
|
},
|
||||||
"git": {
|
"git": {
|
||||||
"pre-commit": "lint-staged"
|
"pre-commit": "lint-staged"
|
||||||
|
@@ -10,17 +10,16 @@
|
|||||||
"lint:fix": "prettier --write .",
|
"lint:fix": "prettier --write .",
|
||||||
"build": "next build",
|
"build": "next build",
|
||||||
"build:standalone": "NEXT_PUBLIC_BASE_PATH=/ui/v2/login NEXT_OUTPUT_MODE=standalone next build",
|
"build:standalone": "NEXT_PUBLIC_BASE_PATH=/ui/v2/login NEXT_OUTPUT_MODE=standalone next build",
|
||||||
"start": "npm run build && next start",
|
"start": "next start",
|
||||||
"start:built": "next start",
|
"clean": "rm -rf node_modules && rm -rf .next"
|
||||||
"clean": "rm -rf .turbo && rm -rf node_modules && rm -rf .next"
|
|
||||||
},
|
},
|
||||||
"dependencies": {
|
"dependencies": {
|
||||||
"@headlessui/react": "^2.1.9",
|
"@headlessui/react": "^2.1.9",
|
||||||
"@heroicons/react": "2.1.3",
|
"@heroicons/react": "2.1.3",
|
||||||
"@tailwindcss/forms": "0.5.7",
|
"@tailwindcss/forms": "0.5.7",
|
||||||
"@vercel/analytics": "^1.2.2",
|
"@vercel/analytics": "^1.2.2",
|
||||||
"@zitadel/client": "^1.0.0",
|
"@zitadel/client": "latest",
|
||||||
"@zitadel/proto": "^1.0.0",
|
"@zitadel/proto": "latest",
|
||||||
"clsx": "1.2.1",
|
"clsx": "1.2.1",
|
||||||
"copy-to-clipboard": "^3.3.3",
|
"copy-to-clipboard": "^3.3.3",
|
||||||
"deepmerge": "^4.3.1",
|
"deepmerge": "^4.3.1",
|
||||||
@@ -41,26 +40,19 @@
|
|||||||
"@bufbuild/buf": "^1.53.0",
|
"@bufbuild/buf": "^1.53.0",
|
||||||
"@testing-library/jest-dom": "^6.6.3",
|
"@testing-library/jest-dom": "^6.6.3",
|
||||||
"@testing-library/react": "^16.3.0",
|
"@testing-library/react": "^16.3.0",
|
||||||
"@types/ms": "2.1.0",
|
|
||||||
"@types/node": "^22.14.1",
|
"@types/node": "^22.14.1",
|
||||||
"@types/react": "19.1.2",
|
"@types/react": "19.1.2",
|
||||||
"@types/react-dom": "19.1.2",
|
"@types/react-dom": "19.1.2",
|
||||||
"@types/tinycolor2": "1.4.3",
|
"@types/tinycolor2": "1.4.3",
|
||||||
"@types/uuid": "^10.0.0",
|
"@types/uuid": "^10.0.0",
|
||||||
"@vercel/git-hooks": "1.0.0",
|
|
||||||
"eslint": "8.57.1",
|
|
||||||
"eslint-config-next": "15.4.0-canary.86",
|
|
||||||
"prettier": "^3.5.3",
|
|
||||||
"autoprefixer": "10.4.21",
|
"autoprefixer": "10.4.21",
|
||||||
"grpc-tools": "1.13.0",
|
|
||||||
"jsdom": "^26.1.0",
|
"jsdom": "^26.1.0",
|
||||||
"make-dir-cli": "4.0.0",
|
|
||||||
"postcss": "8.5.3",
|
"postcss": "8.5.3",
|
||||||
|
"prettier": "^3.2.5",
|
||||||
"prettier-plugin-tailwindcss": "0.6.11",
|
"prettier-plugin-tailwindcss": "0.6.11",
|
||||||
"sass": "^1.87.0",
|
"sass": "^1.87.0",
|
||||||
"tailwindcss": "3.4.14",
|
"tailwindcss": "3.4.14",
|
||||||
"ts-proto": "^2.7.0",
|
|
||||||
"typescript": "^5.8.3",
|
"typescript": "^5.8.3",
|
||||||
"vitest": "^3.1.2"
|
"vitest": "^2.0.0"
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@@ -3,24 +3,54 @@
|
|||||||
# Script to prepare standalone version of the login app
|
# Script to prepare standalone version of the login app
|
||||||
set -e
|
set -e
|
||||||
|
|
||||||
echo "Preparing standalone version..."
|
echo "🔧 Preparing standalone version..."
|
||||||
|
|
||||||
# Copy standalone configs
|
# Parse arguments
|
||||||
cp package.standalone.json package.json
|
INSTALL_DEPS=true
|
||||||
cp tsconfig.standalone.json tsconfig.json
|
USE_LATEST=false
|
||||||
cp .eslintrc.standalone.cjs .eslintrc.cjs
|
|
||||||
cp prettier.config.standalone.mjs prettier.config.mjs
|
|
||||||
cp tailwind.config.standalone.mjs tailwind.config.mjs
|
|
||||||
|
|
||||||
# Install dependencies unless --no-install is passed
|
for arg in "$@"; do
|
||||||
if [ "$1" != "--no-install" ]; then
|
case $arg in
|
||||||
echo "Installing dependencies..."
|
--no-install)
|
||||||
npm install
|
INSTALL_DEPS=false
|
||||||
|
shift
|
||||||
|
;;
|
||||||
|
--latest)
|
||||||
|
USE_LATEST=true
|
||||||
|
shift
|
||||||
|
;;
|
||||||
|
*)
|
||||||
|
# Unknown option
|
||||||
|
;;
|
||||||
|
esac
|
||||||
|
done
|
||||||
|
|
||||||
|
# Build arguments for Node.js script
|
||||||
|
NODE_ARGS=""
|
||||||
|
if [ "$INSTALL_DEPS" = true ]; then
|
||||||
|
NODE_ARGS="$NODE_ARGS --install"
|
||||||
|
fi
|
||||||
|
if [ "$USE_LATEST" = true ]; then
|
||||||
|
NODE_ARGS="$NODE_ARGS --latest"
|
||||||
fi
|
fi
|
||||||
|
|
||||||
echo "Standalone version prepared successfully!"
|
# Check if Node.js scripts exist
|
||||||
if [ "$1" != "--no-install" ]; then
|
if [ ! -f "scripts/prepare-standalone.js" ]; then
|
||||||
echo "You can now run:"
|
echo "❌ scripts/prepare-standalone.js not found!"
|
||||||
|
echo " Make sure you're in the correct directory"
|
||||||
|
exit 1
|
||||||
|
fi
|
||||||
|
|
||||||
|
# Run the enhanced Node.js prepare script
|
||||||
|
node scripts/prepare-standalone.js $NODE_ARGS
|
||||||
|
|
||||||
|
echo ""
|
||||||
|
echo "✅ Standalone version prepared successfully!"
|
||||||
|
|
||||||
|
if [ "$INSTALL_DEPS" = false ]; then
|
||||||
|
echo ""
|
||||||
|
echo "📝 Next steps:"
|
||||||
|
echo " npm install - Install dependencies"
|
||||||
echo " npm run dev - Start development server"
|
echo " npm run dev - Start development server"
|
||||||
echo " npm run build - Build for production"
|
echo " npm run build - Build for production"
|
||||||
echo " npm run start - Start production server"
|
echo " npm run start - Start production server"
|
||||||
|
@@ -1 +1,8 @@
|
|||||||
export { default } from "@zitadel/prettier-config";
|
export default {
|
||||||
|
semi: true,
|
||||||
|
trailingComma: "all",
|
||||||
|
singleQuote: false,
|
||||||
|
printWidth: 80,
|
||||||
|
tabWidth: 2,
|
||||||
|
plugins: ["prettier-plugin-tailwindcss"],
|
||||||
|
};
|
||||||
|
247
login/apps/login/scripts/README.md
Normal file
247
login/apps/login/scripts/README.md
Normal file
@@ -0,0 +1,247 @@
|
|||||||
|
# Standalone Build Scripts
|
||||||
|
|
||||||
|
This directory contains the minimal scripts needed for managing the ZITADEL Login UI standalone conversion.
|
||||||
|
|
||||||
|
## 📁 File Overview
|
||||||
|
|
||||||
|
### Required Files
|
||||||
|
|
||||||
|
- `package.json` - Main package file (monorepo mode with `workspace:*`)
|
||||||
|
- `package.standalone.json` - Pre-configured standalone version (uses `latest`)
|
||||||
|
- `*.standalone.*` - Configuration templates for standalone mode
|
||||||
|
- `scripts/` - Conversion scripts
|
||||||
|
|
||||||
|
### Generated/Temporary Files
|
||||||
|
|
||||||
|
- `*.generated.*` - Temporary files (ignored by git)
|
||||||
|
- `package.monorepo.backup.json` - Backup when switching modes
|
||||||
|
|
||||||
|
## 🛠️ Scripts Overview
|
||||||
|
|
||||||
|
### `prepare-standalone.js`
|
||||||
|
|
||||||
|
**The main script for converting monorepo to standalone mode.**
|
||||||
|
|
||||||
|
```bash
|
||||||
|
node scripts/prepare-standalone.js [--install]
|
||||||
|
```
|
||||||
|
|
||||||
|
- `--install` - Automatically install dependencies after preparation
|
||||||
|
|
||||||
|
**What it does:**
|
||||||
|
|
||||||
|
- Copies `package.standalone.json` → `package.json`
|
||||||
|
- Copies all `*.standalone.*` config files to their active versions
|
||||||
|
- Optionally runs `npm install`
|
||||||
|
|
||||||
|
## 🚀 **Simplified Approach**
|
||||||
|
|
||||||
|
This setup now uses a **much simpler approach**:
|
||||||
|
|
||||||
|
1. **Static Configuration**: `package.standalone.json` is pre-configured with `latest` versions
|
||||||
|
2. **No Version Fetching**: No network calls or complex version management
|
||||||
|
3. **Manual Maintenance**: Package versions are updated manually when needed
|
||||||
|
4. **Faster Setup**: Conversion is instant with just file copying
|
||||||
|
|
||||||
|
## 📋 **Usage for Customers**
|
||||||
|
|
||||||
|
```bash
|
||||||
|
# 1. Clone the repository
|
||||||
|
git clone <standalone-repo>
|
||||||
|
|
||||||
|
# 2. Prepare standalone mode
|
||||||
|
./prepare-standalone.sh --install
|
||||||
|
|
||||||
|
# 3. Start developing
|
||||||
|
npm run dev
|
||||||
|
```
|
||||||
|
|
||||||
|
## 🔧 **Usage for Maintainers**
|
||||||
|
|
||||||
|
```bash
|
||||||
|
# Update to latest packages manually in package.standalone.json
|
||||||
|
npm view @zitadel/client version
|
||||||
|
npm view @zitadel/proto version
|
||||||
|
|
||||||
|
# Then update package.standalone.json with latest versions
|
||||||
|
```
|
||||||
|
|
||||||
|
**What it does:**
|
||||||
|
|
||||||
|
- Converts `workspace:*` dependencies to published package versions
|
||||||
|
- Removes monorepo-specific devDependencies
|
||||||
|
- Copies standalone configuration files
|
||||||
|
- Updates package.json scripts for standalone use
|
||||||
|
|
||||||
|
### `build-standalone.js`
|
||||||
|
|
||||||
|
**Generates package.standalone.json with latest published package versions.**
|
||||||
|
|
||||||
|
```bash
|
||||||
|
node scripts/build-standalone.js
|
||||||
|
```
|
||||||
|
|
||||||
|
**What it does:**
|
||||||
|
|
||||||
|
- Fetches latest versions of `@zitadel/client` and `@zitadel/proto`
|
||||||
|
- Creates a standalone-ready package.json
|
||||||
|
- Safe to run in monorepo (doesn't modify current package.json)
|
||||||
|
|
||||||
|
### `config-manager.js`
|
||||||
|
|
||||||
|
**Utility for switching between monorepo and standalone configurations.**
|
||||||
|
|
||||||
|
```bash
|
||||||
|
# Show current mode
|
||||||
|
node scripts/config-manager.js status
|
||||||
|
|
||||||
|
# Switch to standalone mode
|
||||||
|
node scripts/config-manager.js switch standalone
|
||||||
|
|
||||||
|
# Switch back to monorepo mode
|
||||||
|
node scripts/config-manager.js switch monorepo
|
||||||
|
```
|
||||||
|
|
||||||
|
### `validate-standalone.js`
|
||||||
|
|
||||||
|
**Validates that standalone setup is working correctly.**
|
||||||
|
|
||||||
|
```bash
|
||||||
|
node scripts/validate-standalone.js
|
||||||
|
```
|
||||||
|
|
||||||
|
**Checks:**
|
||||||
|
|
||||||
|
- Required files exist
|
||||||
|
- Package.json has required scripts and dependencies
|
||||||
|
- Dependencies can be resolved
|
||||||
|
- TypeScript compilation works
|
||||||
|
|
||||||
|
## Workflow Examples
|
||||||
|
|
||||||
|
### For Developers (Monorepo)
|
||||||
|
|
||||||
|
1. **Working in monorepo:**
|
||||||
|
|
||||||
|
```bash
|
||||||
|
# Normal development - uses workspace:* dependencies
|
||||||
|
pnpm dev
|
||||||
|
```
|
||||||
|
|
||||||
|
2. **Testing standalone version:**
|
||||||
|
|
||||||
|
```bash
|
||||||
|
# Generate standalone package.json (safe, doesn't modify current setup)
|
||||||
|
node scripts/build-standalone.js
|
||||||
|
|
||||||
|
# Switch to standalone mode for testing
|
||||||
|
node scripts/config-manager.js switch standalone
|
||||||
|
npm install
|
||||||
|
npm run dev
|
||||||
|
|
||||||
|
# Switch back to monorepo mode
|
||||||
|
node scripts/config-manager.js switch monorepo
|
||||||
|
```
|
||||||
|
|
||||||
|
### For Customers (Standalone)
|
||||||
|
|
||||||
|
1. **Initial setup:**
|
||||||
|
|
||||||
|
```bash
|
||||||
|
git clone <standalone-repo>
|
||||||
|
cd login
|
||||||
|
./prepare-standalone.sh --install
|
||||||
|
```
|
||||||
|
|
||||||
|
2. **Development:**
|
||||||
|
|
||||||
|
```bash
|
||||||
|
npm run dev
|
||||||
|
```
|
||||||
|
|
||||||
|
3. **Production:**
|
||||||
|
```bash
|
||||||
|
npm run build:standalone
|
||||||
|
npm run start
|
||||||
|
```
|
||||||
|
|
||||||
|
### For CI/CD (Package Publishing)
|
||||||
|
|
||||||
|
1. **After publishing new @zitadel packages:**
|
||||||
|
|
||||||
|
```bash
|
||||||
|
# Update standalone version with latest packages
|
||||||
|
node scripts/build-standalone.js
|
||||||
|
|
||||||
|
# Commit and push to standalone branch/repo
|
||||||
|
git add package.standalone.json
|
||||||
|
git commit -m "Update standalone package versions"
|
||||||
|
git push origin standalone
|
||||||
|
```
|
||||||
|
|
||||||
|
## Configuration Files
|
||||||
|
|
||||||
|
The scripts manage these configuration files:
|
||||||
|
|
||||||
|
- `package.standalone.json` - Standalone version of package.json
|
||||||
|
- `tsconfig.standalone.json` - TypeScript config for standalone
|
||||||
|
- `.eslintrc.standalone.cjs` - ESLint config for standalone
|
||||||
|
- `prettier.config.standalone.mjs` - Prettier config for standalone
|
||||||
|
- `tailwind.config.standalone.mjs` - Tailwind config for standalone
|
||||||
|
|
||||||
|
## File Structure
|
||||||
|
|
||||||
|
```
|
||||||
|
scripts/
|
||||||
|
├── prepare-standalone.js # Main preparation script
|
||||||
|
├── build-standalone.js # Package.json generator
|
||||||
|
├── config-manager.js # Configuration switcher
|
||||||
|
└── README.md # This file
|
||||||
|
|
||||||
|
# Configuration files
|
||||||
|
├── package.json # Current active package.json
|
||||||
|
├── package.standalone.json # Generated standalone version
|
||||||
|
├── tsconfig.json # Current active TypeScript config
|
||||||
|
├── tsconfig.standalone.json # Standalone TypeScript config
|
||||||
|
├── .eslintrc.cjs # Current active ESLint config
|
||||||
|
├── .eslintrc.standalone.cjs # Standalone ESLint config
|
||||||
|
└── ...
|
||||||
|
```
|
||||||
|
|
||||||
|
## Troubleshooting
|
||||||
|
|
||||||
|
### "Could not fetch latest version" warnings
|
||||||
|
|
||||||
|
This is normal when packages haven't been published yet or npm registry is slow. The scripts will fall back to existing versions.
|
||||||
|
|
||||||
|
### Configuration file not found
|
||||||
|
|
||||||
|
Some configuration files are optional. The scripts will warn but continue without them.
|
||||||
|
|
||||||
|
### Permission denied on scripts
|
||||||
|
|
||||||
|
Make sure scripts are executable:
|
||||||
|
|
||||||
|
```bash
|
||||||
|
chmod +x scripts/*.js
|
||||||
|
chmod +x prepare-standalone.sh
|
||||||
|
```
|
||||||
|
|
||||||
|
### Package version conflicts
|
||||||
|
|
||||||
|
If you encounter version conflicts, try:
|
||||||
|
|
||||||
|
```bash
|
||||||
|
# Clean install
|
||||||
|
rm -rf node_modules package-lock.json
|
||||||
|
npm install
|
||||||
|
```
|
||||||
|
|
||||||
|
## Integration with Monorepo
|
||||||
|
|
||||||
|
These scripts are designed to work seamlessly with the existing monorepo structure:
|
||||||
|
|
||||||
|
- **Development**: Use normal `pnpm` commands in monorepo
|
||||||
|
- **Testing**: Use `config-manager.js` to test standalone mode
|
||||||
|
- **Publishing**: Use `build-standalone.js` to generate updated standalone configs
|
||||||
|
- **Customer Distribution**: Use `prepare-standalone.sh` for easy setup
|
104
login/apps/login/scripts/prepare-standalone.js
Normal file
104
login/apps/login/scripts/prepare-standalone.js
Normal file
@@ -0,0 +1,104 @@
|
|||||||
|
#!/usr/bin/env node
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Prepare script for standalone version
|
||||||
|
* This script converts the monorepo version to a standalone version
|
||||||
|
*/
|
||||||
|
|
||||||
|
import fs from 'fs/promises';
|
||||||
|
import { execSync } from 'child_process';
|
||||||
|
|
||||||
|
const CONFIG_FILES = [
|
||||||
|
{
|
||||||
|
source: 'tsconfig.standalone.json',
|
||||||
|
target: 'tsconfig.json',
|
||||||
|
required: true
|
||||||
|
},
|
||||||
|
{
|
||||||
|
source: '.eslintrc.standalone.cjs',
|
||||||
|
target: '.eslintrc.cjs',
|
||||||
|
required: false
|
||||||
|
},
|
||||||
|
{
|
||||||
|
source: 'prettier.config.standalone.mjs',
|
||||||
|
target: 'prettier.config.mjs',
|
||||||
|
required: false
|
||||||
|
},
|
||||||
|
{
|
||||||
|
source: 'tailwind.config.standalone.mjs',
|
||||||
|
target: 'tailwind.config.mjs',
|
||||||
|
required: false
|
||||||
|
}
|
||||||
|
];
|
||||||
|
|
||||||
|
async function prepareStandalone() {
|
||||||
|
console.log('🔧 Preparing standalone version...\n');
|
||||||
|
|
||||||
|
const args = process.argv.slice(2);
|
||||||
|
const shouldInstall = args.includes('--install');
|
||||||
|
|
||||||
|
try {
|
||||||
|
// Step 1: Copy package.standalone.json to package.json
|
||||||
|
console.log('📦 Setting up package.json...');
|
||||||
|
const packageStandaloneExists = await fs.access('package.standalone.json').then(() => true).catch(() => false);
|
||||||
|
|
||||||
|
if (packageStandaloneExists) {
|
||||||
|
// Backup current package.json
|
||||||
|
await fs.copyFile('package.json', 'package.monorepo.backup.json');
|
||||||
|
console.log(' 💾 Backed up package.json → package.monorepo.backup.json');
|
||||||
|
|
||||||
|
// Copy standalone version
|
||||||
|
await fs.copyFile('package.standalone.json', 'package.json');
|
||||||
|
console.log(' ✅ package.standalone.json → package.json');
|
||||||
|
} else {
|
||||||
|
throw new Error('package.standalone.json not found!');
|
||||||
|
}
|
||||||
|
|
||||||
|
// Step 2: Copy configuration files
|
||||||
|
console.log('\n⚙️ Setting up configuration files...');
|
||||||
|
for (const config of CONFIG_FILES) {
|
||||||
|
try {
|
||||||
|
const sourceExists = await fs.access(config.source).then(() => true).catch(() => false);
|
||||||
|
if (sourceExists) {
|
||||||
|
await fs.copyFile(config.source, config.target);
|
||||||
|
console.log(` ✅ ${config.source} → ${config.target}`);
|
||||||
|
} else if (config.required) {
|
||||||
|
throw new Error(`Required file ${config.source} not found!`);
|
||||||
|
} else {
|
||||||
|
console.log(` ⚠️ ${config.source} not found, skipping`);
|
||||||
|
}
|
||||||
|
} catch (error) {
|
||||||
|
if (config.required) {
|
||||||
|
throw error;
|
||||||
|
}
|
||||||
|
console.warn(` ❌ Failed to copy ${config.source}: ${error.message}`);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Step 3: Install dependencies if requested
|
||||||
|
if (shouldInstall) {
|
||||||
|
console.log('\n📥 Installing dependencies...');
|
||||||
|
try {
|
||||||
|
execSync('npm install', { stdio: 'inherit' });
|
||||||
|
console.log(' ✅ Dependencies installed successfully');
|
||||||
|
} catch (error) {
|
||||||
|
console.warn(' ⚠️ npm install failed, you may need to run it manually');
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
console.log('\n🎉 Standalone preparation complete!');
|
||||||
|
console.log('\n📋 Next steps:');
|
||||||
|
if (!shouldInstall) {
|
||||||
|
console.log(' 1. Run: npm install');
|
||||||
|
}
|
||||||
|
console.log(' 2. Run: npm run dev');
|
||||||
|
console.log(' 3. Start developing!\n');
|
||||||
|
|
||||||
|
} catch (error) {
|
||||||
|
console.error('\n❌ Failed to prepare standalone version:', error.message);
|
||||||
|
console.error('Please check the error above and try again.\n');
|
||||||
|
process.exit(1);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
prepareStandalone();
|
@@ -1,115 +1,15 @@
|
|||||||
import sharedConfig from "@zitadel/tailwind-config/tailwind.config.mjs";
|
|
||||||
|
|
||||||
let colors = {
|
|
||||||
background: { light: { contrast: {} }, dark: { contrast: {} } },
|
|
||||||
primary: { light: { contrast: {} }, dark: { contrast: {} } },
|
|
||||||
warn: { light: { contrast: {} }, dark: { contrast: {} } },
|
|
||||||
text: { light: { contrast: {} }, dark: { contrast: {} } },
|
|
||||||
link: { light: { contrast: {} }, dark: { contrast: {} } },
|
|
||||||
};
|
|
||||||
|
|
||||||
const shades = [
|
|
||||||
"50",
|
|
||||||
"100",
|
|
||||||
"200",
|
|
||||||
"300",
|
|
||||||
"400",
|
|
||||||
"500",
|
|
||||||
"600",
|
|
||||||
"700",
|
|
||||||
"800",
|
|
||||||
"900",
|
|
||||||
];
|
|
||||||
const themes = ["light", "dark"];
|
|
||||||
const types = ["background", "primary", "warn", "text", "link"];
|
|
||||||
types.forEach((type) => {
|
|
||||||
themes.forEach((theme) => {
|
|
||||||
shades.forEach((shade) => {
|
|
||||||
colors[type][theme][shade] = `var(--theme-${theme}-${type}-${shade})`;
|
|
||||||
colors[type][theme][`contrast-${shade}`] =
|
|
||||||
`var(--theme-${theme}-${type}-contrast-${shade})`;
|
|
||||||
colors[type][theme][`secondary-${shade}`] =
|
|
||||||
`var(--theme-${theme}-${type}-secondary-${shade})`;
|
|
||||||
});
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
/** @type {import('tailwindcss').Config} */
|
/** @type {import('tailwindcss').Config} */
|
||||||
export default {
|
export default {
|
||||||
presets: [sharedConfig],
|
content: [
|
||||||
darkMode: "class",
|
"./src/pages/**/*.{js,ts,jsx,tsx,mdx}",
|
||||||
content: ["./src/**/*.{js,ts,jsx,tsx}"],
|
"./src/components/**/*.{js,ts,jsx,tsx,mdx}",
|
||||||
future: {
|
"./src/app/**/*.{js,ts,jsx,tsx,mdx}",
|
||||||
hoverOnlyWhenSupported: true,
|
],
|
||||||
},
|
|
||||||
theme: {
|
theme: {
|
||||||
extend: {
|
extend: {
|
||||||
colors: {
|
colors: {
|
||||||
...colors,
|
background: "var(--background)",
|
||||||
state: {
|
foreground: "var(--foreground)",
|
||||||
success: {
|
|
||||||
light: {
|
|
||||||
background: "#cbf4c9",
|
|
||||||
color: "#0e6245",
|
|
||||||
},
|
|
||||||
dark: {
|
|
||||||
background: "#68cf8340",
|
|
||||||
color: "#cbf4c9",
|
|
||||||
},
|
|
||||||
},
|
|
||||||
error: {
|
|
||||||
light: {
|
|
||||||
background: "#ffc1c1",
|
|
||||||
color: "#620e0e",
|
|
||||||
},
|
|
||||||
dark: {
|
|
||||||
background: "#af455359",
|
|
||||||
color: "#ffc1c1",
|
|
||||||
},
|
|
||||||
},
|
|
||||||
neutral: {
|
|
||||||
light: {
|
|
||||||
background: "#e4e7e4",
|
|
||||||
color: "#000000",
|
|
||||||
},
|
|
||||||
dark: {
|
|
||||||
background: "#1a253c",
|
|
||||||
color: "#ffffff",
|
|
||||||
},
|
|
||||||
},
|
|
||||||
alert: {
|
|
||||||
light: {
|
|
||||||
background: "#fbbf24",
|
|
||||||
color: "#92400e",
|
|
||||||
},
|
|
||||||
dark: {
|
|
||||||
background: "#92400e50",
|
|
||||||
color: "#fbbf24",
|
|
||||||
},
|
|
||||||
},
|
|
||||||
},
|
|
||||||
},
|
|
||||||
animation: {
|
|
||||||
shake: "shake .8s cubic-bezier(.36,.07,.19,.97) both;",
|
|
||||||
},
|
|
||||||
keyframes: {
|
|
||||||
shake: {
|
|
||||||
"10%, 90%": {
|
|
||||||
transform: "translate3d(-1px, 0, 0)",
|
|
||||||
},
|
|
||||||
|
|
||||||
"20%, 80%": {
|
|
||||||
transform: "translate3d(2px, 0, 0)",
|
|
||||||
},
|
|
||||||
|
|
||||||
"30%, 50%, 70%": {
|
|
||||||
transform: "translate3d(-4px, 0, 0)",
|
|
||||||
},
|
|
||||||
|
|
||||||
"40%, 60%": {
|
|
||||||
transform: "translate3d(4px, 0, 0)",
|
|
||||||
},
|
|
||||||
},
|
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
|
31
login/apps/login/tsconfig.json
Executable file → Normal file
31
login/apps/login/tsconfig.json
Executable file → Normal file
@@ -1,24 +1,27 @@
|
|||||||
{
|
{
|
||||||
"extends": "@zitadel/tsconfig/nextjs.json",
|
|
||||||
"compilerOptions": {
|
"compilerOptions": {
|
||||||
|
"target": "es5",
|
||||||
|
"lib": ["dom", "dom.iterable", "esnext"],
|
||||||
|
"allowJs": true,
|
||||||
|
"skipLibCheck": true,
|
||||||
|
"strict": true,
|
||||||
|
"noEmit": true,
|
||||||
|
"esModuleInterop": true,
|
||||||
|
"module": "esnext",
|
||||||
|
"moduleResolution": "bundler",
|
||||||
|
"resolveJsonModule": true,
|
||||||
|
"isolatedModules": true,
|
||||||
"jsx": "preserve",
|
"jsx": "preserve",
|
||||||
"target": "es2022",
|
"incremental": true,
|
||||||
"baseUrl": ".",
|
|
||||||
"paths": {
|
|
||||||
"@/*": ["./src/*"]
|
|
||||||
},
|
|
||||||
"plugins": [
|
"plugins": [
|
||||||
{
|
{
|
||||||
"name": "next"
|
"name": "next"
|
||||||
}
|
}
|
||||||
]
|
|
||||||
},
|
|
||||||
"include": [
|
|
||||||
"next-env.d.ts",
|
|
||||||
"**/*.ts",
|
|
||||||
"**/*.tsx",
|
|
||||||
".next/types/**/*.ts",
|
|
||||||
"custom-config.js"
|
|
||||||
],
|
],
|
||||||
|
"paths": {
|
||||||
|
"@/*": ["./src/*"]
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"include": ["next-env.d.ts", "**/*.ts", "**/*.tsx", ".next/types/**/*.ts"],
|
||||||
"exclude": ["node_modules"]
|
"exclude": ["node_modules"]
|
||||||
}
|
}
|
||||||
|
@@ -5,6 +5,10 @@
|
|||||||
"access": "public"
|
"access": "public"
|
||||||
},
|
},
|
||||||
"main": "index.js",
|
"main": "index.js",
|
||||||
|
"exports": {
|
||||||
|
".": "./index.js",
|
||||||
|
"./tailwind.config.mjs": "./tailwind.config.mjs"
|
||||||
|
},
|
||||||
"devDependencies": {
|
"devDependencies": {
|
||||||
"tailwindcss": "^4.1.4",
|
"tailwindcss": "^4.1.4",
|
||||||
"@tailwindcss/forms": "0.5.3"
|
"@tailwindcss/forms": "0.5.3"
|
||||||
|
Reference in New Issue
Block a user