Compare commits

..
Author SHA1 Message Date
Eldad A. FuxandGitHub a5fa09b4ce Merge pull request #11185 from Shivangisharma4/doc-fix-typos-contributing
doc: Fix typos in CONTRIBUTING.md
2026-02-27 20:42:57 +01:00
10e2edac90 Update CONTRIBUTING.md
Co-authored-by: Copilot <175728472+Copilot@users.noreply.github.com>
2026-01-24 14:03:11 +05:30
Shivangisharma4 340081a67d doc: Fix typos in CONTRIBUTING.md 2026-01-24 13:58:20 +05:30
7688 changed files with 827024 additions and 80726 deletions
-31
View File
@@ -1,31 +0,0 @@
# PR Workflow for Appwrite
## Branch Targeting
**Important:** Appwrite does NOT use `main` as the primary development branch.
PRs should target the **current version branch** (e.g., `1.8.x`, `1.9.x`), not `main`.
### How to determine the correct target branch
1. Check which version branch you're currently on: `git branch --show-current`
2. Look for branches matching the pattern `X.Y.x` (e.g., `1.8.x`, `1.9.x`)
3. The current active development branch is typically the highest version number with the `.x` suffix
### When creating PRs
Always use the version branch as the base:
```bash
# Correct - targets the version branch
gh pr create --base 1.8.x --title "Your PR title" --body "..."
# Wrong - do not target main
gh pr create --base main ...
```
### Branch naming convention
- `X.Y.x` branches (e.g., `1.8.x`) - Active development branches for each minor version
- `main` - Not used for regular PRs; reserved for release management
- Feature branches should be created from and merged back into the current version branch
+4 -22
View File
@@ -2,7 +2,6 @@ _APP_ENV=development
_APP_EDITION=self-hosted
_APP_LOCALE=en
_APP_WORKER_PER_CORE=6
_APP_COMPRESSION_ENABLED=enabled
_APP_COMPRESSION_MIN_SIZE_BYTES=1024
_APP_CONSOLE_WHITELIST_ROOT=disabled
_APP_CONSOLE_WHITELIST_EMAILS=
@@ -10,7 +9,6 @@ _APP_CONSOLE_SESSION_ALERTS=enabled
_APP_CONSOLE_WHITELIST_IPS=
_APP_CONSOLE_COUNTRIES_DENYLIST=AQ
_APP_CONSOLE_HOSTNAMES=localhost,appwrite.io,*.appwrite.io
_APP_MIGRATION_HOST=appwrite
_APP_SYSTEM_EMAIL_NAME=Appwrite
_APP_SYSTEM_EMAIL_ADDRESS=noreply@appwrite.io
_APP_SYSTEM_TEAM_EMAIL=team@appwrite.io
@@ -26,9 +24,8 @@ _APP_OPENSSL_KEY_V1=your-secret-key
_APP_DNS=172.16.238.100 # CoreDNS
_APP_DOMAIN=appwrite.test
_APP_CONSOLE_DOMAIN=localhost
_APP_CONSOLE_TRUSTED_PROJECTS=trusted-project,another-trusted-project
_APP_DOMAIN_FUNCTIONS=functions.localhost
_APP_DOMAIN_SITES=sites.localhost,rebranded.localhost
_APP_DOMAIN_SITES=sites.localhost
_APP_DOMAIN_TARGET_CNAME=cname.localhost
_APP_DOMAIN_TARGET_A=203.0.0.1
_APP_DOMAIN_TARGET_AAAA=::1
@@ -38,22 +35,12 @@ _APP_REDIS_HOST=redis
_APP_REDIS_PORT=6379
_APP_REDIS_PASS=
_APP_REDIS_USER=
_APP_DB_ADAPTER=mariadb
_APP_DB_HOST=mariadb
_APP_DB_PORT=3306
_APP_DB_ADAPTER=mariadb
_APP_DB_SCHEMA=appwrite
_APP_DB_USER=user
_APP_DB_PASS=password
_APP_DB_ROOT_PASS=rootsecretpassword
_APP_DB_ADAPTER_DOCUMENTSDB=mongodb
_APP_DB_HOST_DOCUMENTSDB=mongodb
_APP_DB_PORT_DOCUMENTSDB=27017
_APP_DB_ADAPTER_VECTORDB=postgresql
_APP_DB_HOST_VECTORDB=postgresql
_APP_DB_PORT_VECTORDB=5432
_APP_EMBEDDING_MODELS=embeddinggemma
_APP_EMBEDDING_ENDPOINT='http://ollama:11434/api/embed'
_APP_STORAGE_DEVICE=Local
_APP_STORAGE_S3_ACCESS_KEY=
_APP_STORAGE_S3_SECRET=
@@ -82,8 +69,8 @@ _APP_STORAGE_ANTIVIRUS_PORT=3310
_APP_SMTP_HOST=maildev
_APP_SMTP_PORT=1025
_APP_SMTP_SECURE=
_APP_SMTP_USERNAME=user
_APP_SMTP_PASSWORD=password
_APP_SMTP_USERNAME=
_APP_SMTP_PASSWORD=
_APP_SMS_PROVIDER=sms://username:password@mock
_APP_SMS_FROM=+123456789
_APP_SMS_PROJECTS_DENY_LIST=
@@ -114,12 +101,9 @@ _APP_USAGE_AGGREGATION_INTERVAL=30
_APP_STATS_RESOURCES_INTERVAL=30
_APP_MAINTENANCE_RETENTION_USAGE_HOURLY=8640000
_APP_MAINTENANCE_RETENTION_SCHEDULES=86400
_APP_INTERVAL_DOMAIN_VERIFICATION=120
_APP_INTERVAL_CLEANUP_STALE_EXECUTIONS=300
_APP_USAGE_STATS=enabled
_APP_LOGGING_CONFIG=
_APP_LOGGING_CONFIG_REALTIME=
_APP_GRAPHQL_INTROSPECTION=enabled
_APP_GRAPHQL_MAX_BATCH_SIZE=10
_APP_GRAPHQL_MAX_COMPLEXITY=250
_APP_GRAPHQL_MAX_DEPTH=4
@@ -141,6 +125,4 @@ _APP_WEBHOOK_MAX_FAILED_ATTEMPTS=10
_APP_PROJECT_REGIONS=default
_APP_FUNCTIONS_CREATION_ABUSE_LIMIT=5000
_APP_STATS_USAGE_DUAL_WRITING_DBS=database_db_main
_APP_TRUSTED_HEADERS=x-forwarded-for
_APP_POOL_ADAPTER=stack
_APP_WORKER_SCREENSHOTS_ROUTER=http://appwrite
_APP_TRUSTED_HEADERS=x-forwarded-for
+3 -5
View File
@@ -3,7 +3,6 @@ concurrency:
group: '${{ github.workflow }}-${{ github.ref }}'
cancel-in-progress: true
env:
COMPOSE_FILE: docker-compose.yml
IMAGE: appwrite-dev
CACHE_KEY: 'appwrite-dev-${{ github.event.pull_request.head.sha }}'
'on':
@@ -14,7 +13,7 @@ jobs:
runs-on: ubuntu-latest
steps:
- name: Checkout repository
uses: actions/checkout@v6
uses: actions/checkout@v4
with:
submodules: recursive
- name: Set up Docker Buildx
@@ -29,7 +28,6 @@ jobs:
cache-from: type=gha
cache-to: 'type=gha,mode=max'
outputs: 'type=docker,dest=/tmp/${{ env.IMAGE }}.tar'
target: development
build-args: |
DEBUG=false
TESTING=true
@@ -47,7 +45,7 @@ jobs:
pull-requests: write
steps:
- name: Checkout repository
uses: actions/checkout@v6
uses: actions/checkout@v4
- name: Load Cache
uses: actions/cache@v4
with:
@@ -99,7 +97,7 @@ jobs:
echo "| 200 | $(jq -r '.statusCodeDistribution."200"|tostring|[while(length>0;.[:-3])|.[-3:]]|reverse|join(",")' benchmark.json) | $(jq -r '.statusCodeDistribution."200"|tostring|[while(length>0;.[:-3])|.[-3:]]|reverse|join(",")' benchmark-latest.json) | " >> benchmark.txt
echo "| P99 | $(jq -r '.latencyPercentiles.p99' benchmark.json ) | $(jq -r '.latencyPercentiles.p99' benchmark-latest.json ) | " >> benchmark.txt
- name: Save results
uses: actions/upload-artifact@v6
uses: actions/upload-artifact@v4
if: '${{ !cancelled() }}'
with:
name: benchmark.json
+1 -1
View File
@@ -10,7 +10,7 @@ jobs:
runs-on: ubuntu-latest
steps:
- name: Check out code
uses: actions/checkout@v6
uses: actions/checkout@v4
- name: Cleanup
run: |
+1 -1
View File
@@ -34,7 +34,7 @@ jobs:
steps:
- name: Checkout repository
uses: actions/checkout@v6
uses: actions/checkout@v4
with:
# We must fetch at least the immediate parents so that if this is
# a pull request then we can checkout the head.
+3 -3
View File
@@ -12,7 +12,7 @@ jobs:
steps:
- name: Checkout repository
uses: actions/checkout@v6
uses: actions/checkout@v4
with:
fetch-depth: 2
@@ -20,9 +20,9 @@ jobs:
- name: Validate composer.json and composer.lock
run: |
docker run --rm -v $PWD:/app composer:2.8 sh -c \
docker run --rm -v $PWD:/app composer sh -c \
"composer validate"
- name: Run Linter
run: |
docker run --rm -v $PWD:/app composer:2.8 sh -c \
docker run --rm -v $PWD:/app composer sh -c \
"composer install --profile --ignore-platform-reqs && composer lint"
+3 -3
View File
@@ -10,11 +10,11 @@ jobs:
runs-on: ubuntu-latest
steps:
- name: Check out code
uses: actions/checkout@v6
uses: actions/checkout@v4
with:
submodules: recursive
- name: Build the Docker image
run: DOCKER_BUILDKIT=1 docker build . --target production -t appwrite_image:latest
run: docker build . -t appwrite_image:latest
- name: Run Trivy vulnerability scanner on image
uses: aquasecurity/trivy-action@0.20.0
with:
@@ -33,7 +33,7 @@ jobs:
runs-on: ubuntu-latest
steps:
- name: Check out code
uses: actions/checkout@v6
uses: actions/checkout@v4
- name: Run Trivy vulnerability scanner on filesystem
uses: aquasecurity/trivy-action@0.20.0
with:
+4 -5
View File
@@ -11,20 +11,19 @@ jobs:
pull-requests: write
steps:
- name: Check out code
uses: actions/checkout@v6
uses: actions/checkout@v4
with:
ref: ${{ github.event.pull_request.head.sha }}
fetch-depth: 0
submodules: 'recursive'
- name: Build the Docker image
uses: docker/build-push-action@v6
with:
uses: docker/build-push-action@v5
with:
context: .
push: false
load: true
tags: pr_image:${{ github.sha }}
target: production
- name: Run Trivy vulnerability scanner on image
uses: aquasecurity/trivy-action@0.20.0
@@ -45,7 +44,7 @@ jobs:
- name: Process Trivy scan results
id: process-results
uses: actions/github-script@v8
uses: actions/github-script@v7
with:
script: |
const fs = require('fs');
+3 -3
View File
@@ -12,7 +12,7 @@ jobs:
steps:
- name: Checkout repository
uses: actions/checkout@v6
uses: actions/checkout@v4
with:
fetch-depth: 2
submodules: recursive
@@ -24,7 +24,7 @@ jobs:
uses: docker/setup-buildx-action@v3
- name: Login to Docker Hub
uses: docker/login-action@v3
uses: docker/login-action@v2
with:
username: ${{ vars.DOCKERHUB_USERNAME }}
password: ${{ secrets.DOCKERHUB_TOKEN }}
@@ -38,7 +38,7 @@ jobs:
type=ref,event=tag
- name: Build & Publish to DockerHub
uses: docker/build-push-action@v6
uses: docker/build-push-action@v4
with:
context: .
platforms: linux/amd64,linux/arm64
+3 -3
View File
@@ -11,7 +11,7 @@ jobs:
steps:
- name: Checkout repository
uses: actions/checkout@v6
uses: actions/checkout@v4
with:
# We must fetch at least the immediate parents so that if this is
# a pull request then we can checkout the head.
@@ -26,7 +26,7 @@ jobs:
uses: docker/setup-buildx-action@v3
- name: Login to Docker Hub
uses: docker/login-action@v3
uses: docker/login-action@v2
with:
username: ${{ vars.DOCKERHUB_USERNAME }}
password: ${{ secrets.DOCKERHUB_TOKEN }}
@@ -42,7 +42,7 @@ jobs:
type=semver,pattern={{major}}
- name: Build and push
uses: docker/build-push-action@v6
uses: docker/build-push-action@v4
with:
context: .
platforms: linux/amd64,linux/arm64
+5 -12
View File
@@ -1,9 +1,9 @@
name: "SDK Preview"
env:
COMPOSE_FILE: docker-compose.yml
on:
pull_request:
paths:
- 'app/config/specs/*-latest-console.json'
workflow_dispatch:
inputs:
platform:
@@ -19,7 +19,7 @@ jobs:
runs-on: ubuntu-latest
steps:
- name: Checkout repository
uses: actions/checkout@v6
uses: actions/checkout@v4
- name: Set SDK type
id: set-sdk
@@ -39,13 +39,6 @@ jobs:
run: |
docker compose build
docker compose up -d
- name: Generate Specs
run: |
docker compose exec appwrite specs --version=latest --mode=normal --git=no
- name: Generate SDK
run: |
docker compose exec appwrite sdks --platform=${{ steps.set-sdk.outputs.platform }} --sdk=${{ steps.set-sdk.outputs.sdk_type }} --version=latest --git=no
sudo chown -R $USER:$USER ./app/sdks/${{ steps.set-sdk.outputs.platform }}-${{ steps.set-sdk.outputs.sdk_type }}
@@ -54,7 +47,7 @@ jobs:
node-version: 20
- name: Build and Publish SDK
working-directory: ./app/sdks/${{ steps.set-sdk.outputs.platform }}-${{ steps.set-sdk.outputs.sdk_type }}
working-directory: ./app/sdks/console-web
run: |
npm install
npm run build
-113
View File
@@ -1,113 +0,0 @@
name: "Generate Specs"
env:
COMPOSE_FILE: docker-compose.yml
on:
workflow_dispatch:
inputs:
version:
type: choice
description: "Appwrite version to generate specs for"
required: true
options:
- "1.8.x"
- "1.7.x"
- "1.6.x"
- "1.5.x"
- "latest"
push:
type: boolean
description: "Push specs to appwrite/specs repo and create PR"
default: true
message:
type: string
description: "Commit message for the specs PR"
default: "chore: update API specs and SDK examples"
jobs:
generate:
name: Generate Specs
runs-on: ubuntu-latest
steps:
- name: Checkout repository
uses: actions/checkout@v6
with:
submodules: recursive
- name: Build and start Appwrite
run: |
docker compose build
docker compose up -d
- name: Generate specs
run: |
docker compose exec appwrite specs --version=${{ inputs.version }} --mode=normal --git=no
- name: Generate SDK examples
if: inputs.push
run: |
docker compose exec appwrite sdks --platform=* --sdk=* --version=${{ inputs.version }} --git=no --mode=examples
sudo chown -R $USER:$USER ./docs/examples/
- name: Push to appwrite/specs and create PR
if: inputs.push
env:
GH_TOKEN: ${{ secrets.GITHUB_TOKEN }}
run: |
VERSION="${{ inputs.version }}"
MESSAGE="${{ inputs.message }}"
GIT_BRANCH="feat-${VERSION}-specs"
SPECS_DIR="./app/config/specs"
EXAMPLES_DIR="./docs/examples/${VERSION}"
TARGET="/tmp/specs-repo"
sudo chown -R $USER:$USER "${SPECS_DIR}"
# Clone the specs repo
git clone "https://x-access-token:${GH_TOKEN}@github.com/appwrite/specs.git" "${TARGET}"
cd "${TARGET}"
git config user.name "github-actions[bot]"
git config user.email "github-actions[bot]@users.noreply.github.com"
# Create or checkout the feature branch
git checkout -b "${GIT_BRANCH}" || git checkout "${GIT_BRANCH}"
# Copy spec files
mkdir -p "specs/${VERSION}"
cp ${GITHUB_WORKSPACE}/${SPECS_DIR}/*${VERSION}*.json "specs/${VERSION}/" 2>/dev/null || true
# Copy latest specs if version is latest
if [ "${VERSION}" = "latest" ]; then
cp ${GITHUB_WORKSPACE}/${SPECS_DIR}/*latest*.json "specs/latest/" 2>/dev/null || true
fi
# Copy SDK examples
if [ -d "${GITHUB_WORKSPACE}/docs/examples/${VERSION}" ]; then
mkdir -p "examples/${VERSION}"
cp -r "${GITHUB_WORKSPACE}/docs/examples/${VERSION}/." "examples/${VERSION}/"
fi
# Commit and push
git add -A
git diff --cached --quiet && echo "No changes to commit" && exit 0
git commit -m "${MESSAGE}"
git push -u origin "${GIT_BRANCH}" --force
# Create or update PR
EXISTING_PR=$(gh pr list --repo appwrite/specs --head "${GIT_BRANCH}" --json number --jq '.[0].number' 2>/dev/null || true)
if [ -n "${EXISTING_PR}" ]; then
echo "PR #${EXISTING_PR} already exists, updated branch"
echo "https://github.com/appwrite/specs/pull/${EXISTING_PR}"
else
gh pr create \
--repo "appwrite/specs" \
--title "feat: API specs update for version ${VERSION}" \
--body "This PR contains API specification updates and SDK examples for version ${VERSION}." \
--base "main" \
--head "${GIT_BRANCH}"
fi
- name: Stop containers
if: always()
run: docker compose down
+2 -2
View File
@@ -8,11 +8,11 @@ jobs:
steps:
- name: Check out the repo
uses: actions/checkout@v6
uses: actions/checkout@v4
- name: Run CodeQL
run: |
docker run --rm -v $PWD:/app composer:2.8 sh -c \
docker run --rm -v $PWD:/app composer:2.6 sh -c \
"composer install --profile --ignore-platform-reqs && composer check"
- name: Run Locale check
+103 -223
View File
@@ -5,7 +5,6 @@ concurrency:
cancel-in-progress: true
env:
COMPOSE_FILE: docker-compose.yml
IMAGE: appwrite-dev
CACHE_KEY: appwrite-dev-${{ github.event.pull_request.head.sha }}
@@ -27,7 +26,7 @@ jobs:
database_changed: ${{ steps.check.outputs.database_changed }}
steps:
- name: Checkout repository
uses: actions/checkout@v6
uses: actions/checkout@v4
- name: Fetch base branch
run: git fetch origin ${{ github.event.pull_request.base.ref }}
@@ -49,7 +48,7 @@ jobs:
runs-on: ubuntu-latest
steps:
- name: Checkout repository
uses: actions/checkout@v6
uses: actions/checkout@v4
with:
submodules: recursive
@@ -66,7 +65,6 @@ jobs:
cache-from: type=gha
cache-to: type=gha,mode=max
outputs: type=docker,dest=/tmp/${{ env.IMAGE }}.tar
target: development
build-args: |
DEBUG=false
TESTING=true
@@ -82,13 +80,10 @@ jobs:
name: Unit Test
runs-on: ubuntu-latest
needs: setup
permissions:
contents: read
pull-requests: write
steps:
- name: checkout
uses: actions/checkout@v6
uses: actions/checkout@v4
- name: Load Cache
uses: actions/cache@v4
@@ -113,28 +108,18 @@ jobs:
run: docker compose exec -T appwrite vars
- name: Run Unit Tests
uses: itznotabug/php-retry@v3
with:
max_attempts: 3
timeout_minutes: 30
job_id: ${{ job.check_run_id }}
github_token: ${{ secrets.GITHUB_TOKEN }}
test_dir: tests/unit
command: >-
docker compose exec
-e _APP_E2E_RESPONSE_FORMAT="${{ github.event.inputs.response_format }}"
run: |
docker compose exec \
-e _APP_E2E_RESPONSE_FORMAT="${{ github.event.inputs.response_format }}" \
appwrite test /usr/src/code/tests/unit
e2e_general_test:
name: E2E General Test
runs-on: ubuntu-latest
needs: setup
permissions:
contents: read
pull-requests: write
steps:
- name: checkout
uses: actions/checkout@v6
uses: actions/checkout@v4
- name: Load Cache
uses: actions/cache@v4
@@ -158,47 +143,32 @@ jobs:
done
- name: Run General Tests
uses: itznotabug/php-retry@v3
with:
max_attempts: 3
timeout_minutes: 30
job_id: ${{ job.check_run_id }}
github_token: ${{ secrets.GITHUB_TOKEN }}
test_dir: tests/e2e/General
command: >-
docker compose exec -T
-e _APP_E2E_RESPONSE_FORMAT="${{ github.event.inputs.response_format }}"
run: |
docker compose exec -T \
-e _APP_E2E_RESPONSE_FORMAT="${{ github.event.inputs.response_format }}" \
appwrite test /usr/src/code/tests/e2e/General --debug
- name: Failure Logs
if: failure()
run: |
echo "=== Appwrite Logs ==="
docker compose logs
echo "=== Appwrite Worker Builds Logs ==="
docker compose logs appwrite-worker-builds
echo "=== OpenRuntimes Executor Logs ==="
docker compose logs openruntimes-executor
e2e_service_test:
name: E2E Service Test
runs-on: ubuntu-latest
needs: setup
permissions:
contents: read
pull-requests: write
strategy:
fail-fast: false
matrix:
db_adapter: [
MARIADB,
POSTGRESQL,
# MONGODB
]
service: [
Account,
Avatars,
Console,
Databases/Legacy,
Databases/TablesDB,
Databases/DocumentsDB,
Databases/VectorDB,
Functions,
FunctionsSchedule,
GraphQL,
@@ -219,7 +189,7 @@ jobs:
]
steps:
- name: Checkout repository
uses: actions/checkout@v6
uses: actions/checkout@v4
- name: Load Cache
uses: actions/cache@v4
@@ -232,18 +202,6 @@ jobs:
run: |
docker load --input /tmp/${{ env.IMAGE }}.tar
sed -i 's|^_APP_BROWSER_HOST=.*|_APP_BROWSER_HOST=http://invalid-browser/v1|' .env
# Set DB Adapter in .env before starting services
if [ "${{ matrix.db_adapter }}" = "MARIADB" ]; then
sed -i 's|^_APP_DB_ADAPTER=.*|_APP_DB_ADAPTER=mariadb|' .env
sed -i 's|^_APP_DB_HOST=.*|_APP_DB_HOST=mariadb|' .env
sed -i 's|^_APP_DB_PORT=.*|_APP_DB_PORT=3306|' .env
elif [ "${{ matrix.db_adapter }}" = "MONGODB" ]; then
sed -i 's|^_APP_DB_ADAPTER=.*|_APP_DB_ADAPTER=mongodb|' .env
sed -i 's|^_APP_DB_HOST=.*|_APP_DB_HOST=mongodb|' .env
sed -i 's|^_APP_DB_PORT=.*|_APP_DB_PORT=27017|' .env
fi
docker compose up -d
sleep 30
@@ -256,44 +214,16 @@ jobs:
done
- name: Run ${{ matrix.service }} tests with Project table mode
uses: itznotabug/php-retry@v3
with:
max_attempts: 3
timeout_minutes: 30
job_id: ${{ job.check_run_id }}
github_token: ${{ secrets.GITHUB_TOKEN }}
test_dir: tests/e2e/Services/${{ matrix.service }}
command: |
echo "Using project tables"
run: |
echo "Using project tables"
export _APP_DATABASE_SHARED_TABLES=
export _APP_DATABASE_SHARED_TABLES_V1=
export _APP_DATABASE_SHARED_TABLES=
export _APP_DATABASE_SHARED_TABLES_V1=
# Set DB Adapter Specific ENV Vars using if-elif
if [ "${{ matrix.db_adapter }}" = "MARIADB" ]; then
export _APP_DB_ADAPTER=mariadb
export _APP_DB_HOST=mariadb
export _APP_DB_PORT=3306
export _APP_DB_SCHEMA=appwrite
elif [ "${{ matrix.db_adapter }}" = "POSTGRESQL" ]; then
export _APP_DB_ADAPTER=postgresql
export _APP_DB_HOST=postgresql
export _APP_DB_PORT=5432
export _APP_DB_SCHEMA=appwrite
else
echo "Unknown DB adapter: ${{ matrix.db_adapter }}"
exit 1
fi
docker compose exec -T \
-e _APP_DATABASE_SHARED_TABLES \
-e _APP_DATABASE_SHARED_TABLES_V1 \
-e _APP_DB_ADAPTER \
-e _APP_DB_HOST \
-e _APP_DB_PORT \
-e _APP_DB_SCHEMA \
-e _APP_E2E_RESPONSE_FORMAT="${{ github.event.inputs.response_format }}" \
appwrite test /usr/src/code/tests/e2e/Services/${{ matrix.service }} --debug --exclude-group abuseEnabled,screenshots
docker compose exec -T \
-e _APP_DATABASE_SHARED_TABLES \
-e _APP_DATABASE_SHARED_TABLES_V1 \
-e _APP_E2E_RESPONSE_FORMAT="${{ github.event.inputs.response_format }}" \
appwrite test /usr/src/code/tests/e2e/Services/${{ matrix.service }} --debug --exclude-group devKeys,screenshots
- name: Failure Logs
if: failure()
@@ -308,9 +238,6 @@ jobs:
runs-on: ubuntu-latest
needs: [ setup, check_database_changes ]
if: needs.check_database_changes.outputs.database_changed == 'true'
permissions:
contents: read
pull-requests: write
strategy:
fail-fast: false
matrix:
@@ -346,7 +273,7 @@ jobs:
steps:
- name: checkout
uses: actions/checkout@v6
uses: actions/checkout@v4
- name: Load Cache
uses: actions/cache@v4
@@ -370,29 +297,22 @@ jobs:
done
- name: Run ${{ matrix.service }} tests with ${{ matrix.tables-mode }} table mode
uses: itznotabug/php-retry@v3
with:
max_attempts: 3
timeout_minutes: 30
job_id: ${{ job.check_run_id }}
github_token: ${{ secrets.GITHUB_TOKEN }}
test_dir: tests/e2e/Services/${{ matrix.service }}
command: |
if [ "${{ matrix.tables-mode }}" == "Shared V1" ]; then
echo "Using shared tables V1"
export _APP_DATABASE_SHARED_TABLES=database_db_main
export _APP_DATABASE_SHARED_TABLES_V1=database_db_main
elif [ "${{ matrix.tables-mode }}" == "Shared V2" ]; then
echo "Using shared tables V2"
export _APP_DATABASE_SHARED_TABLES=database_db_main
export _APP_DATABASE_SHARED_TABLES_V1=
fi
docker compose exec -T \
-e _APP_DATABASE_SHARED_TABLES \
-e _APP_DATABASE_SHARED_TABLES_V1 \
-e _APP_E2E_RESPONSE_FORMAT="${{ github.event.inputs.response_format }}" \
appwrite test /usr/src/code/tests/e2e/Services/${{ matrix.service }} --debug --exclude-group abuseEnabled,screenshots
run: |
if [ "${{ matrix.tables-mode }}" == "Shared V1" ]; then
echo "Using shared tables V1"
export _APP_DATABASE_SHARED_TABLES=database_db_main
export _APP_DATABASE_SHARED_TABLES_V1=database_db_main
elif [ "${{ matrix.tables-mode }}" == "Shared V2" ]; then
echo "Using shared tables V2"
export _APP_DATABASE_SHARED_TABLES=database_db_main
export _APP_DATABASE_SHARED_TABLES_V1=
fi
docker compose exec -T \
-e _APP_DATABASE_SHARED_TABLES \
-e _APP_DATABASE_SHARED_TABLES_V1 \
-e _APP_E2E_RESPONSE_FORMAT="${{ github.event.inputs.response_format }}" \
appwrite test /usr/src/code/tests/e2e/Services/${{ matrix.service }} --debug --exclude-group devKeys,screenshots
- name: Failure Logs
if: failure()
@@ -402,16 +322,13 @@ jobs:
echo "=== OpenRuntimes Executor Logs ==="
docker compose logs openruntimes-executor
e2e_abuse_enabled:
name: E2E Service Test (Abuse enabled)
e2e_dev_keys:
name: E2E Service Test (Dev Keys)
runs-on: ubuntu-latest
needs: setup
permissions:
contents: read
pull-requests: write
steps:
- name: checkout
uses: actions/checkout@v6
uses: actions/checkout@v4
- name: Load Cache
uses: actions/cache@v4
@@ -427,24 +344,17 @@ jobs:
docker compose up -d
sleep 30
- name: Run Projects tests in dedicated table mode
uses: itznotabug/php-retry@v3
with:
max_attempts: 3
timeout_minutes: 30
job_id: ${{ job.check_run_id }}
github_token: ${{ secrets.GITHUB_TOKEN }}
test_dir: tests/e2e/Services/Projects
command: |
echo "Using project tables"
export _APP_DATABASE_SHARED_TABLES=
export _APP_DATABASE_SHARED_TABLES_V1=
- name: Run Projects tests with dev keys in dedicated table mode
run: |
echo "Using project tables"
export _APP_DATABASE_SHARED_TABLES=
export _APP_DATABASE_SHARED_TABLES_V1=
docker compose exec -T \
-e _APP_DATABASE_SHARED_TABLES \
-e _APP_DATABASE_SHARED_TABLES_V1 \
-e _APP_E2E_RESPONSE_FORMAT="${{ github.event.inputs.response_format }}" \
appwrite test /usr/src/code/tests/e2e/Services/Projects --debug --group=abuseEnabled
docker compose exec -T \
-e _APP_DATABASE_SHARED_TABLES \
-e _APP_DATABASE_SHARED_TABLES_V1 \
-e _APP_E2E_RESPONSE_FORMAT="${{ github.event.inputs.response_format }}" \
appwrite test /usr/src/code/tests/e2e/Services/Projects --debug --group=devKeys
- name: Failure Logs
if: failure()
@@ -454,14 +364,11 @@ jobs:
echo "=== OpenRuntimes Executor Logs ==="
docker compose logs openruntimes-executor
e2e_abuse_enabled_shared_mode:
name: E2E Shared Mode Service Test (Abuse enabled)
e2e_dev_keys_shared_mode:
name: E2E Shared Mode Service Test (Dev Keys)
runs-on: ubuntu-latest
needs: [ setup, check_database_changes ]
if: needs.check_database_changes.outputs.database_changed == 'true'
permissions:
contents: read
pull-requests: write
strategy:
fail-fast: false
matrix:
@@ -471,7 +378,7 @@ jobs:
]
steps:
- name: checkout
uses: actions/checkout@v6
uses: actions/checkout@v4
- name: Load Cache
uses: actions/cache@v4
@@ -487,30 +394,23 @@ jobs:
docker compose up -d
sleep 30
- name: Run Projects tests in ${{ matrix.tables-mode }} table mode
uses: itznotabug/php-retry@v3
with:
max_attempts: 3
timeout_minutes: 30
job_id: ${{ job.check_run_id }}
github_token: ${{ secrets.GITHUB_TOKEN }}
test_dir: tests/e2e/Services/Projects
command: |
if [ "${{ matrix.tables-mode }}" == "Shared V1" ]; then
echo "Using shared tables V1"
export _APP_DATABASE_SHARED_TABLES=database_db_main
export _APP_DATABASE_SHARED_TABLES_V1=database_db_main
elif [ "${{ matrix.tables-mode }}" == "Shared V2" ]; then
echo "Using shared tables V2"
export _APP_DATABASE_SHARED_TABLES=database_db_main
export _APP_DATABASE_SHARED_TABLES_V1=
fi
- name: Run Projects tests with dev keys in ${{ matrix.tables-mode }} table mode
run: |
if [ "${{ matrix.tables-mode }}" == "Shared V1" ]; then
echo "Using shared tables V1"
export _APP_DATABASE_SHARED_TABLES=database_db_main
export _APP_DATABASE_SHARED_TABLES_V1=database_db_main
elif [ "${{ matrix.tables-mode }}" == "Shared V2" ]; then
echo "Using shared tables V2"
export _APP_DATABASE_SHARED_TABLES=database_db_main
export _APP_DATABASE_SHARED_TABLES_V1=
fi
docker compose exec -T \
-e _APP_DATABASE_SHARED_TABLES \
-e _APP_DATABASE_SHARED_TABLES_V1 \
-e _APP_E2E_RESPONSE_FORMAT="${{ github.event.inputs.response_format }}" \
appwrite test /usr/src/code/tests/e2e/Services/Projects --debug --group=abuseEnabled
docker compose exec -T \
-e _APP_DATABASE_SHARED_TABLES \
-e _APP_DATABASE_SHARED_TABLES_V1 \
-e _APP_E2E_RESPONSE_FORMAT="${{ github.event.inputs.response_format }}" \
appwrite test /usr/src/code/tests/e2e/Services/Projects --debug --group=devKeys
- name: Failure Logs
if: failure()
@@ -520,16 +420,13 @@ jobs:
echo "=== OpenRuntimes Executor Logs ==="
docker compose logs openruntimes-executor
e2e_screenshots:
e2e_screenshots_keys:
name: E2E Service Test (Site Screenshots)
runs-on: ubuntu-latest
needs: setup
permissions:
contents: read
pull-requests: write
steps:
- name: checkout
uses: actions/checkout@v6
uses: actions/checkout@v4
- name: Load Cache
uses: actions/cache@v4
@@ -546,24 +443,17 @@ jobs:
sleep 30
- name: Run Site tests with browser connected in dedicated table mode
uses: itznotabug/php-retry@v3
with:
max_attempts: 3
timeout_minutes: 30
job_id: ${{ job.check_run_id }}
github_token: ${{ secrets.GITHUB_TOKEN }}
test_dir: tests/e2e/Services/Sites
command: |
echo "Keeping original value of _APP_BROWSER_HOST"
echo "Using project tables"
export _APP_DATABASE_SHARED_TABLES=
export _APP_DATABASE_SHARED_TABLES_V1=
run: |
echo "Keeping original value of _APP_BROWSER_HOST"
echo "Using project tables"
export _APP_DATABASE_SHARED_TABLES=
export _APP_DATABASE_SHARED_TABLES_V1=
docker compose exec -T \
-e _APP_DATABASE_SHARED_TABLES \
-e _APP_DATABASE_SHARED_TABLES_V1 \
-e _APP_E2E_RESPONSE_FORMAT="${{ github.event.inputs.response_format }}" \
appwrite test /usr/src/code/tests/e2e/Services/Sites --debug --group=screenshots
docker compose exec -T \
-e _APP_DATABASE_SHARED_TABLES \
-e _APP_DATABASE_SHARED_TABLES_V1 \
-e _APP_E2E_RESPONSE_FORMAT="${{ github.event.inputs.response_format }}" \
appwrite test /usr/src/code/tests/e2e/Services/Sites --debug --group=screenshots
- name: Failure Logs
if: failure()
@@ -578,9 +468,6 @@ jobs:
runs-on: ubuntu-latest
needs: [ setup, check_database_changes ]
if: needs.check_database_changes.outputs.database_changed == 'true'
permissions:
contents: read
pull-requests: write
strategy:
fail-fast: false
matrix:
@@ -590,7 +477,7 @@ jobs:
]
steps:
- name: checkout
uses: actions/checkout@v6
uses: actions/checkout@v4
- name: Load Cache
uses: actions/cache@v4
@@ -607,30 +494,23 @@ jobs:
sleep 30
- name: Run Site tests with browser connected in ${{ matrix.tables-mode }} table mode
uses: itznotabug/php-retry@v3
with:
max_attempts: 3
timeout_minutes: 30
job_id: ${{ job.check_run_id }}
github_token: ${{ secrets.GITHUB_TOKEN }}
test_dir: tests/e2e/Services/Sites
command: |
echo "Keeping original value of _APP_BROWSER_HOST"
if [ "${{ matrix.tables-mode }}" == "Shared V1" ]; then
echo "Using shared tables V1"
export _APP_DATABASE_SHARED_TABLES=database_db_main
export _APP_DATABASE_SHARED_TABLES_V1=database_db_main
elif [ "${{ matrix.tables-mode }}" == "Shared V2" ]; then
echo "Using shared tables V2"
export _APP_DATABASE_SHARED_TABLES=database_db_main
export _APP_DATABASE_SHARED_TABLES_V1=
fi
run: |
echo "Keeping original value of _APP_BROWSER_HOST"
if [ "${{ matrix.tables-mode }}" == "Shared V1" ]; then
echo "Using shared tables V1"
export _APP_DATABASE_SHARED_TABLES=database_db_main
export _APP_DATABASE_SHARED_TABLES_V1=database_db_main
elif [ "${{ matrix.tables-mode }}" == "Shared V2" ]; then
echo "Using shared tables V2"
export _APP_DATABASE_SHARED_TABLES=database_db_main
export _APP_DATABASE_SHARED_TABLES_V1=
fi
docker compose exec -T \
-e _APP_DATABASE_SHARED_TABLES \
-e _APP_DATABASE_SHARED_TABLES_V1 \
-e _APP_E2E_RESPONSE_FORMAT="${{ github.event.inputs.response_format }}" \
appwrite test /usr/src/code/tests/e2e/Services/Sites --debug --group=screenshots
docker compose exec -T \
-e _APP_DATABASE_SHARED_TABLES \
-e _APP_DATABASE_SHARED_TABLES_V1 \
-e _APP_E2E_RESPONSE_FORMAT="${{ github.event.inputs.response_format }}" \
appwrite test /usr/src/code/tests/e2e/Services/Sites --debug --group=screenshots
- name: Failure Logs
if: failure()
@@ -638,4 +518,4 @@ jobs:
echo "=== Appwrite Worker Builds Logs ==="
docker compose logs appwrite-worker-builds
echo "=== OpenRuntimes Executor Logs ==="
docker compose logs openruntimes-executor
docker compose logs openruntimes-executor
+1 -2
View File
@@ -17,5 +17,4 @@ dev/yasd_init.php
.phpunit.result.cache
Makefile
appwrite.config.json
/.zed/
/app/config/specs/
/.zed/
-77
View File
@@ -1,77 +0,0 @@
# AGENTS.md
Appwrite is an end-to-end backend server for web, mobile, native, and backend apps. This guide provides context and instructions for AI coding agents working on the Appwrite codebase.
## Project Overview
Appwrite is a self-hosted Backend-as-a-Service (BaaS) platform that provides developers with a set of APIs and tools to build secure, scalable applications. The project uses a hybrid monolithic-microservice architecture built with PHP, running on Swoole for high performance.
**Key Technologies:**
- **Backend:** PHP 8.3+, Swoole
- **Libraries:** Utopia PHP
- **Database:** MariaDB, Redis
- **Cache:** Redis
- **Queue:** Redis
- **Containers:** Docker
## Development Commands
```bash
# Run Appwrite
docker compose up -d --force-recreate --build
# Run specific test
docker compose exec appwrite test /usr/src/code/tests/e2e/Services/[ServiceName] --filter=[FunctionName]
# Format code
composer format
```
## Code Style Guidelines
- Follow [PSR-12](https://www.php-fig.org/psr/psr-12/) coding standard
- Use PSR-4 autoloading
- Strict type declarations where applicable
- Comprehensive PHPDoc comments
### Naming Conventions
#### `resourceType` Naming Rule
When a collection has a combination of `resourceType`, `resourceId`, and/or `resourceInternalId`, the value of `resourceType` MUST always be **plural** - for example: `functions`, `sites`, `deployments`.
Examples:
```php
'resourceType' => 'functions'
'resourceType' => 'sites'
'resourceType' => 'deployments'
```
## Security Considerations
### Critical Security Practices
- **Never hardcode credentials** - Use environment variables
- **Rate limiting** - Respect abuse prevention mechanisms
## Dependencies
Avoid introducing new dependencies other than utopia-php.
## Adding new endpoints
When adding new endpoints, make sure to use modules and follow its patterns. Find instruction in [Modules AGENTS.md](src/Appwrite/Platform/AGENTS.md) file.
## Pull Request Guidelines
### Before Submitting
- Run `composer format`
- Update documentation if adding features
- Add/update tests for your changes
- Check that Docker build succeeds
`docs/specs/authentication.drawio.svg`
## Known Issues and Gotchas
- **Hot Reload:** Code changes require container restart in some cases
- **Logging:** There is no central place for logs, so when debugging, ensure to check all possibly relevant containers
-98
View File
@@ -1,101 +1,3 @@
# Version 1.8.1
## What's Changed
### Notable changes
* Add branch deployments support in [#10486](https://github.com/appwrite/appwrite/pull/10486)
* Add TanStack Start sites support in [#10681](https://github.com/appwrite/appwrite/pull/10681)
* Add Next.js standalone support in [#10747](https://github.com/appwrite/appwrite/pull/10747)
* Add Resend integration in [#10690](https://github.com/appwrite/appwrite/pull/10690)
* Add option to enable/disable image transformations per-bucket in [#10722](https://github.com/appwrite/appwrite/pull/10722)
* Add operators support in [#10735](https://github.com/appwrite/appwrite/pull/10735) and [#10800](https://github.com/appwrite/appwrite/pull/10800)
* Add function and sites stats in [#10786](https://github.com/appwrite/appwrite/pull/10786)
* Add disable count feature in [#10668](https://github.com/appwrite/appwrite/pull/10668)
* Add ElevenLabs site template in [#10782](https://github.com/appwrite/appwrite/pull/10782)
* Add suggested environment variables in [#10795](https://github.com/appwrite/appwrite/pull/10795)
* Update GeoDB database in [#10890](https://github.com/appwrite/appwrite/pull/10890)
* Update Flutter default build runtime in [#10807](https://github.com/appwrite/appwrite/pull/10807)
* Upgrade runtimes in [#10804](https://github.com/appwrite/appwrite/pull/10804)
### Fixes
* Fix duplicate document error while creating file in [#10891](https://github.com/appwrite/appwrite/pull/10891)
* Fix "Update external deployment (authorize)" throwing 500 error due to invalid query in [#10888](https://github.com/appwrite/appwrite/pull/10888)
* Fix error setting user password in [#10889](https://github.com/appwrite/appwrite/pull/10889)
* Fix error generating email MFA challenges in [#10884](https://github.com/appwrite/appwrite/pull/10884)
* Fix file token expiry in [#10877](https://github.com/appwrite/appwrite/pull/10877)
* Fix TanStack Nitro default in [#10860](https://github.com/appwrite/appwrite/pull/10860)
* Fix TanStack builds in [#10767](https://github.com/appwrite/appwrite/pull/10767)
* Fix nullable validation in [#10819](https://github.com/appwrite/appwrite/pull/10819) and [#10778](https://github.com/appwrite/appwrite/pull/10778)
* Fix WebP library in [#10738](https://github.com/appwrite/appwrite/pull/10738)
* Fix batch writes in [#10812](https://github.com/appwrite/appwrite/pull/10812)
* Fix error handler error in [#10719](https://github.com/appwrite/appwrite/pull/10719)
* Fix Next 16 compatibility in [#10713](https://github.com/appwrite/appwrite/pull/10713)
* Fix stats usage memory leak in [#10683](https://github.com/appwrite/appwrite/pull/10683)
* Fix author URL in template deployments in [#10535](https://github.com/appwrite/appwrite/pull/10535)
* Fix VCS lock deletion in [#10691](https://github.com/appwrite/appwrite/pull/10691)
### Miscellaneous
* Add CSV export functionality in [#10546](https://github.com/appwrite/appwrite/pull/10546), [#10750](https://github.com/appwrite/appwrite/pull/10750), [#10813](https://github.com/appwrite/appwrite/pull/10813), and [#10847](https://github.com/appwrite/appwrite/pull/10847)
* Add JWT disposition in [#10867](https://github.com/appwrite/appwrite/pull/10867)
* Add screenshots endpoint in [#10675](https://github.com/appwrite/appwrite/pull/10675)
* Add screenshot endpoint stats in [#10706](https://github.com/appwrite/appwrite/pull/10706)
* Add users attributes in [#10688](https://github.com/appwrite/appwrite/pull/10688)
* Add max build duration environment variable in [#10674](https://github.com/appwrite/appwrite/pull/10674)
* Add custom realtime logger in [#10871](https://github.com/appwrite/appwrite/pull/10871)
* Add logs in [#10869](https://github.com/appwrite/appwrite/pull/10869)
* Improve MFA docs endpoint order in [#10793](https://github.com/appwrite/appwrite/pull/10793)
* Auth refactor in [#10758](https://github.com/appwrite/appwrite/pull/10758), [#10837](https://github.com/appwrite/appwrite/pull/10837), [#10682](https://github.com/appwrite/appwrite/pull/10682), and [#10667](https://github.com/appwrite/appwrite/pull/10667)
* Bump assistant to 0.8.4 in [#10887](https://github.com/appwrite/appwrite/pull/10887)
* Bump database to 3.1.5 in [#10766](https://github.com/appwrite/appwrite/pull/10766)
* Bump Utopia DNS in [#10761](https://github.com/appwrite/appwrite/pull/10761)
* Update domains to 0.8.3 in [#10658](https://github.com/appwrite/appwrite/pull/10658)
* Update domains to 0.9.1 in [#10678](https://github.com/appwrite/appwrite/pull/10678)
* Update Apple Swift to 13.3.0 in [#10679](https://github.com/appwrite/appwrite/pull/10679)
* Update Apple Swift in [#10663](https://github.com/appwrite/appwrite/pull/10663)
* Update CLI to 10.2.2 in [#10672](https://github.com/appwrite/appwrite/pull/10672)
* Update to CLI 12.0.0 in [#10853](https://github.com/appwrite/appwrite/pull/10853)
* Update docs examples to use Permission class in [#10707](https://github.com/appwrite/appwrite/pull/10707)
* Update SDK examples docs in [#10855](https://github.com/appwrite/appwrite/pull/10855)
* Release Python SDK in [#10762](https://github.com/appwrite/appwrite/pull/10762)
* Release Flutter 20.3.2 in [#10838](https://github.com/appwrite/appwrite/pull/10838)
* Release Flutter/Dart add screenshot examples in [#10811](https://github.com/appwrite/appwrite/pull/10811)
* Release PHP CLI in [#10791](https://github.com/appwrite/appwrite/pull/10791)
* Release SDKs in [#10817](https://github.com/appwrite/appwrite/pull/10817)
* Update SDKs in [#10694](https://github.com/appwrite/appwrite/pull/10694), [#10729](https://github.com/appwrite/appwrite/pull/10729), and [#10744](https://github.com/appwrite/appwrite/pull/10744)
* Update SDK generator in [#10743](https://github.com/appwrite/appwrite/pull/10743)
* Update database in [#10664](https://github.com/appwrite/appwrite/pull/10664)
* Update README file in [#10763](https://github.com/appwrite/appwrite/pull/10763)
* SDK release documentation in [#10745](https://github.com/appwrite/appwrite/pull/10745)
* SDK release runtime config in [#10765](https://github.com/appwrite/appwrite/pull/10765)
* Sync specs in [#10789](https://github.com/appwrite/appwrite/pull/10789)
* Sync 1.8.0 in [#10677](https://github.com/appwrite/appwrite/pull/10677)
* Add workflow for issue triage in [#10718](https://github.com/appwrite/appwrite/pull/10718)
* Add issue auto-labeler in [#10700](https://github.com/appwrite/appwrite/pull/10700)
* Add AI moderator repo in [#10717](https://github.com/appwrite/appwrite/pull/10717)
* Browser bump in [#10850](https://github.com/appwrite/appwrite/pull/10850)
* Template type enum override in [#10848](https://github.com/appwrite/appwrite/pull/10848)
* VCS reference type in [#10852](https://github.com/appwrite/appwrite/pull/10852)
* Index scope description in [#10851](https://github.com/appwrite/appwrite/pull/10851)
* Config for environment in [#10833](https://github.com/appwrite/appwrite/pull/10833)
* Format instance in [#10830](https://github.com/appwrite/appwrite/pull/10830)
* Replace sleep in webhooks service in [#10656](https://github.com/appwrite/appwrite/pull/10656)
* Update email composer in [#10720](https://github.com/appwrite/appwrite/pull/10720)
* Update facts on GitHub sites and functions in [#10593](https://github.com/appwrite/appwrite/pull/10593) and [#10771](https://github.com/appwrite/appwrite/pull/10771)
* Fix wrong user type in [#10875](https://github.com/appwrite/appwrite/pull/10875)
* Fix limit and offset computation in [#10880](https://github.com/appwrite/appwrite/pull/10880)
* Fix enum examples in [#10828](https://github.com/appwrite/appwrite/pull/10828)
* Fix response models multi-methods in [#10815](https://github.com/appwrite/appwrite/pull/10815)
* Fix undefined variable in [#10654](https://github.com/appwrite/appwrite/pull/10654)
* Fix undefined sequence in [#10652](https://github.com/appwrite/appwrite/pull/10652)
* Fix description in [#10702](https://github.com/appwrite/appwrite/pull/10702)
* Fix warning in builds worker in [#10705](https://github.com/appwrite/appwrite/pull/10705)
* Fix sites create deployment docs in [#10566](https://github.com/appwrite/appwrite/pull/10566)
* Fix test dependencies projects in [#10655](https://github.com/appwrite/appwrite/pull/10655)
* Fix list sites test in [#10726](https://github.com/appwrite/appwrite/pull/10726)
# Version 1.8.0
## What's Changed
+57 -35
View File
@@ -111,7 +111,7 @@ $ git push origin [name_of_your_new_branch]
## Setup From Source
To set up a working **development environment**, just fork the project git repository and install the backend and frontend dependencies using the proper package manager and create run the docker-compose stack.
To set up a working **development environment**, just fork the project git repository and install the backend and frontend dependencies using the proper package manager and run the docker-compose stack.
> If you just want to install Appwrite for day-to-day use and not as a contributor, you can reference the [installation guide](https://github.com/appwrite/appwrite#installation), the [getting started guide](https://appwrite.io/docs/quick-starts), or the main [README](README.md) file.
@@ -173,12 +173,12 @@ Learn more at our [Technology Stack](#technology-stack) section.
- [MVVM](https://en.wikipedia.org/wiki/Model%E2%80%93view%E2%80%93viewmodel) - Appwrite console architecture
##### Container Namespace Conventions
To keep our services easy to understand within Docker we follow a naming convention for all our containers depending on it's intended use.
To keep our services easy to understand within Docker we follow a naming convention for all our containers depending on its intended use.
`appwrite-worker-X` - Workers (`src/Appwrite/Platform/Workers/*`)
`appwrite-task-X` - Tasks (`src/Appwrite/Platform/Tasks/*`)
Other containes should be named the same as their service, for example `redis` should just be called `redis`.
Other containers should be named the same as their service, for example `redis` should just be called `redis`.
##### Security
@@ -189,7 +189,7 @@ Other containes should be named the same as their service, for example `redis` s
## Modules
As Appwrite grows, we noticed approach of having all service endpoints in `app/controllers/api/[service].php` is not maintainable. Not only it creates massive files, it also doesnt contain all product's features such as workers or tasks. While there might still be some occurances of those controller files, we avoid it in all new development, and gradually migrate existing controllers to **HTTP modules**.
As Appwrite grows, we noticed approach of having all service endpoints in `app/controllers/api/[service].php` is not maintainable. Not only it creates massive files, it also doesn't contain all product's features such as workers or tasks. While there might still be some occurrences of those controller files, we avoid it in all new development, and gradually migrate existing controllers to **HTTP modules**.
### HTTP Endpoints
@@ -204,7 +204,7 @@ Tips and tricks:
1. If endpoint doesn't have resource, use service name as resource name too
> Example: `Modules/Sites/Http/Sites/Get.php`
2. If there are multiple resources, use then all in folder structure
2. If there are multiple resources, use them all in folder structure
> Example: `Modules/Sites/Http/Deployments/Builds/Create.php`
3. Action can only be `Get`, `Create`, `Update`, `Delete` or `XList`
@@ -222,51 +222,73 @@ Appwrite's current structure is a combination of both [Monolithic](https://en.wi
```bash
.
├── app # Main application
│ ├── assets
│ │ ├── dbip
│ │ ├── fonts
│ │ └── security
│ ├── config # Config files
│ │ ├── avatars
│ │ ├── collections
│ │ ├── locale
│ │ ├── specs
│ │ ├── storage
│ │ └── templates
│ ├── controllers # API & dashboard controllers
│ │ ├── api
│ │ ├── shared
│ │ └── web
│ ├── db # DB schemas
├── sdks # SDKs generated copies (used for generating code examples)
── tasks # Server CLI commands
├── views # HTML server-side templates
└── workers # Background workers
│ ├── init # DB schemas
│ └── database
── views # HTML server-side templates
├── general
└── install
├── bin # Server executables (tasks & workers)
├── docker # Docker related resources and configs
├── dev # Debugger config
├── docs # Docs and tutorials
│ ├── examples
│ ├── lists
│ ├── references
│ ├── sdks
│ ├── services
│ ├── specs
│ └── tutorials
├── public # Public files
│ ├── dist
│ ├── fonts
│ ├── images
│ ├── scripts
── styles
├── src # Supporting libraries (each lib has one role, common libs are released as individual projects)
│ └── Appwrite
├── Auth
├── Detector
├── Docker
| ├── DSN
├── Event
├── Extend
├── GraphQL
├── Messaging
├── Migration
├── Network
├── OpenSSL
├── Promises
├── Specification
├── Task
├── Template
├── URL
── Utopia
│ ├── sdk-console
── sdk-project
│ └── sdk-web
├── src # Supporting libraries (each lib has one role, common libs are released as
│ ├── Appwrite
├── Auth
├── Certificates
├── Deletes
├── Detector
├── Docker
├── Event
├── Extend
├── Functions/Validator
├── GraphQL
├── Hooks
├── Messaging
├── Migration
├── Network
├── OpenSSL
├── Platform
── Promises
│ │ ├── PubSub
│ │ ├── SDK
│ │ ├── Task/Validator
│ │ ├── Template
│ │ ├── Transformation
│ │ ├── URL
│ │ ├── Utopia
│ │ └── Vcs
│ └── Executor
└── tests # End to end & unit tests
├── benchmarks
├── e2e
├── extensions
├── resources
└── unit
```
@@ -395,7 +417,7 @@ These are the current metrics we collect usage stats for:
> Note: The curly brackets in the metric name represents a template and is replaced with a value when the metric is processed.
Metrics are collected within 3 scopes Daily, monthly, an infinity. Adding new usage metric in order to aggregate usage stats is very simple, but very much dependent on where do you want to collect
Metrics are collected within 3 scopes Daily, monthly, and infinity. Adding new usage metric in order to aggregate usage stats is very simple, but very much dependent on where do you want to collect
statistics ,via API or via background worker. For both cases you will need to add a `const` variable in `app/init.php` under the usage metrics list using the naming convention `METRIC_<RESOURCE_NAME>` as shown below.
```php
@@ -661,7 +683,7 @@ docker compose exec redis redis-cli FLUSHALL
## Using preview domains locally
Appwrite Functions are automatically given a domain you can visit to execute the function. This domain has format `[SOMETHING].functions.localhost` unless you changed `_APP_DOMAIN_FUNCTIONS` environment variable. This default value works great when running Appwrite locally, but it can be impossible to use preview domains with Cloud woekspaces such as Gitpod or GitHub Codespaces.
Appwrite Functions are automatically given a domain you can visit to execute the function. This domain has format `[SOMETHING].functions.localhost` unless you changed `_APP_DOMAIN_FUNCTIONS` environment variable. This default value works great when running Appwrite locally, but it can be impossible to use preview domains with Cloud workspaces such as Gitpod or GitHub Codespaces.
To use preview domains on Cloud workspaces, you can visit hostname provided by them, and supply function's preview domain as URL parameter:
+1 -7
View File
@@ -12,7 +12,7 @@ RUN composer install --ignore-platform-reqs --optimize-autoloader \
--no-plugins --no-scripts --prefer-dist \
`if [ "$TESTING" != "true" ]; then echo "--no-dev"; fi`
FROM appwrite/base:1.0.0 AS base
FROM appwrite/base:0.10.6 AS base
LABEL maintainer="team@appwrite.io"
@@ -37,9 +37,6 @@ COPY ./app /usr/src/code/app
COPY ./public /usr/src/code/public
COPY ./bin /usr/local/bin
COPY ./src /usr/src/code/src
COPY ./dev /usr/src/code/dev
COPY ./mongo-init.js /usr/src/code/mongo-init.js
COPY ./mongo-entrypoint.sh /usr/src/code/mongo-entrypoint.sh
# Set Volumes
RUN mkdir -p /storage/uploads && \
@@ -60,7 +57,6 @@ RUN mkdir -p /storage/uploads && \
# Executables
RUN chmod +x /usr/local/bin/doctor && \
chmod +x /usr/local/bin/install && \
chmod +x /usr/local/bin/interval && \
chmod +x /usr/local/bin/maintenance && \
chmod +x /usr/local/bin/migrate && \
chmod +x /usr/local/bin/realtime && \
@@ -80,11 +76,9 @@ RUN chmod +x /usr/local/bin/doctor && \
chmod +x /usr/local/bin/queue-count-success && \
chmod +x /usr/local/bin/worker-audits && \
chmod +x /usr/local/bin/worker-builds && \
chmod +x /usr/local/bin/worker-screenshots && \
chmod +x /usr/local/bin/worker-certificates && \
chmod +x /usr/local/bin/worker-databases && \
chmod +x /usr/local/bin/worker-deletes && \
chmod +x /usr/local/bin/worker-executions && \
chmod +x /usr/local/bin/worker-functions && \
chmod +x /usr/local/bin/worker-mails && \
chmod +x /usr/local/bin/worker-messaging && \
+3 -3
View File
@@ -72,7 +72,7 @@ docker run -it --rm \
--volume /var/run/docker.sock:/var/run/docker.sock \
--volume "$(pwd)"/appwrite:/usr/src/code/appwrite:rw \
--entrypoint="install" \
appwrite/appwrite:1.8.1
appwrite/appwrite:1.8.0
```
### Windows
@@ -84,7 +84,7 @@ docker run -it --rm ^
--volume //var/run/docker.sock:/var/run/docker.sock ^
--volume "%cd%"/appwrite:/usr/src/code/appwrite:rw ^
--entrypoint="install" ^
appwrite/appwrite:1.8.1
appwrite/appwrite:1.8.0
```
#### PowerShell
@@ -94,7 +94,7 @@ docker run -it --rm `
--volume /var/run/docker.sock:/var/run/docker.sock `
--volume ${pwd}/appwrite:/usr/src/code/appwrite:rw `
--entrypoint="install" `
appwrite/appwrite:1.8.1
appwrite/appwrite:1.8.0
```
运行后,可以在浏览器上访问 http://localhost 找到 Appwrite 控制台。在非 Linux 的本机主机上完成安装后,服务器可能需要几分钟才能启动。
+3 -3
View File
@@ -75,7 +75,7 @@ docker run -it --rm \
--volume /var/run/docker.sock:/var/run/docker.sock \
--volume "$(pwd)"/appwrite:/usr/src/code/appwrite:rw \
--entrypoint="install" \
appwrite/appwrite:1.8.1
appwrite/appwrite:1.8.0
```
### Windows
@@ -87,7 +87,7 @@ docker run -it --rm ^
--volume //var/run/docker.sock:/var/run/docker.sock ^
--volume "%cd%"/appwrite:/usr/src/code/appwrite:rw ^
--entrypoint="install" ^
appwrite/appwrite:1.8.1
appwrite/appwrite:1.8.0
```
#### PowerShell
@@ -97,7 +97,7 @@ docker run -it --rm `
--volume /var/run/docker.sock:/var/run/docker.sock `
--volume ${pwd}/appwrite:/usr/src/code/appwrite:rw `
--entrypoint="install" `
appwrite/appwrite:1.8.1
appwrite/appwrite:1.8.0
```
Once the Docker installation is complete, go to http://localhost to access the Appwrite console from your browser. Please note that on non-Linux native hosts, the server might take a few minutes to start after completing the installation.
+39 -63
View File
@@ -16,13 +16,13 @@ use Swoole\Timer;
use Utopia\Cache\Adapter\Pool as CachePool;
use Utopia\Cache\Adapter\Sharding;
use Utopia\Cache\Cache;
use Utopia\CLI\CLI;
use Utopia\CLI\Console;
use Utopia\Config\Config;
use Utopia\Console;
use Utopia\Database\Adapter\Pool as DatabasePool;
use Utopia\Database\Database;
use Utopia\Database\Document;
use Utopia\Database\Validator\Authorization;
use Utopia\DI\Dependency;
use Utopia\DSN\DSN;
use Utopia\Logger\Log;
use Utopia\Platform\Service;
@@ -41,33 +41,9 @@ Config::setParam('runtimes', (new Runtimes('v5'))->getAll(supported: false));
// require controllers after overwriting runtimes
require_once __DIR__ . '/controllers/general.php';
global $register;
CLI::setResource('register', fn () => $register);
$platform = new Appwrite();
$args = $platform->getEnv('argv');
\array_shift($args);
if (!isset($args[0])) {
Console::error('Missing task name');
Console::exit(1);
}
$taskName = $args[0];
$platform->init(Service::TYPE_TASK);
$cli = $platform->getCli();
$setResource = function (string $name, callable $callback, array $injections = []) use ($cli) {
$dependency = new Dependency();
$dependency->setName($name)->setCallback($callback);
foreach ($injections as $injection) {
$dependency->inject($injection);
}
$cli->setResource($dependency);
};
$setResource('register', fn () => $register, []);
$setResource('cache', function ($pools) {
CLI::setResource('cache', function ($pools) {
$list = Config::getParam('pools-cache', []);
$adapters = [];
@@ -78,17 +54,17 @@ $setResource('cache', function ($pools) {
return new Cache(new Sharding($adapters));
}, ['pools']);
$setResource('pools', function (Registry $register) {
CLI::setResource('pools', function (Registry $register) {
return $register->get('pools');
}, ['register']);
$setResource('authorization', function () {
CLI::setResource('authorization', function () {
$authorization = new Authorization();
$authorization->disable();
return $authorization;
}, []);
$setResource('dbForPlatform', function ($pools, $cache, $authorization) {
CLI::setResource('dbForPlatform', function ($pools, $cache, $authorization) {
$sleep = 3;
$maxAttempts = 5;
$attempts = 0;
@@ -102,7 +78,6 @@ $setResource('dbForPlatform', function ($pools, $cache, $authorization) {
$dbForPlatform = new Database($adapter, $cache);
$dbForPlatform
->setDatabase(APP_DATABASE)
->setAuthorization($authorization)
->setNamespace('_console')
->setMetadata('host', \gethostname())
@@ -131,17 +106,16 @@ $setResource('dbForPlatform', function ($pools, $cache, $authorization) {
return $dbForPlatform;
}, ['pools', 'cache', 'authorization']);
$setResource('console', function () {
CLI::setResource('console', function () {
return new Document(Config::getParam('console'));
}, []);
$setResource(
CLI::setResource(
'isResourceBlocked',
fn () => fn (Document $project, string $resourceType, ?string $resourceId) => false,
[]
fn () => fn (Document $project, string $resourceType, ?string $resourceId) => false
);
$setResource('getProjectDB', function (Group $pools, Database $dbForPlatform, $cache, $authorization) {
CLI::setResource('getProjectDB', function (Group $pools, Database $dbForPlatform, $cache, $authorization) {
$databases = []; // TODO: @Meldiron This should probably be responsibility of utopia-php/pools
return function (Document $project) use ($pools, $dbForPlatform, $cache, $authorization, &$databases) {
@@ -194,7 +168,6 @@ $setResource('getProjectDB', function (Group $pools, Database $dbForPlatform, $c
}
$database
->setDatabase(APP_DATABASE)
->setAuthorization($authorization)
->setMetadata('host', \gethostname())
->setMetadata('project', $project->getId());
@@ -203,7 +176,7 @@ $setResource('getProjectDB', function (Group $pools, Database $dbForPlatform, $c
};
}, ['pools', 'dbForPlatform', 'cache', 'authorization']);
$setResource('getLogsDB', function (Group $pools, Cache $cache, Authorization $authorization) {
CLI::setResource('getLogsDB', function (Group $pools, Cache $cache, Authorization $authorization) {
$database = null;
return function (?Document $project = null) use ($pools, $cache, $database, $authorization) {
@@ -216,7 +189,6 @@ $setResource('getLogsDB', function (Group $pools, Cache $cache, Authorization $a
$database = new Database($adapter, $cache);
$database
->setDatabase(APP_DATABASE)
->setAuthorization($authorization)
->setSharedTables(true)
->setNamespace('logsV1')
@@ -231,40 +203,40 @@ $setResource('getLogsDB', function (Group $pools, Cache $cache, Authorization $a
return $database;
};
}, ['pools', 'cache', 'authorization']);
$setResource('publisher', function (Group $pools) {
CLI::setResource('publisher', function (Group $pools) {
return new BrokerPool(publisher: $pools->get('publisher'));
}, ['pools']);
$setResource('publisherDatabases', function (BrokerPool $publisher) {
CLI::setResource('publisherDatabases', function (BrokerPool $publisher) {
return $publisher;
}, ['publisher']);
$setResource('publisherFunctions', function (BrokerPool $publisher) {
CLI::setResource('publisherFunctions', function (BrokerPool $publisher) {
return $publisher;
}, ['publisher']);
$setResource('publisherMigrations', function (BrokerPool $publisher) {
CLI::setResource('publisherMigrations', function (BrokerPool $publisher) {
return $publisher;
}, ['publisher']);
$setResource('publisherStatsUsage', function (BrokerPool $publisher) {
CLI::setResource('publisherStatsUsage', function (BrokerPool $publisher) {
return $publisher;
}, ['publisher']);
$setResource('publisherMessaging', function (BrokerPool $publisher) {
CLI::setResource('publisherMessaging', function (BrokerPool $publisher) {
return $publisher;
}, ['publisher']);
$setResource('queueForStatsUsage', function (Publisher $publisher) {
CLI::setResource('queueForStatsUsage', function (Publisher $publisher) {
return new StatsUsage($publisher);
}, ['publisher']);
$setResource('queueForStatsResources', function (Publisher $publisher) {
CLI::setResource('queueForStatsResources', function (Publisher $publisher) {
return new StatsResources($publisher);
}, ['publisher']);
$setResource('queueForFunctions', function (Publisher $publisher) {
CLI::setResource('queueForFunctions', function (Publisher $publisher) {
return new Func($publisher);
}, ['publisher']);
$setResource('queueForDeletes', function (Publisher $publisher) {
CLI::setResource('queueForDeletes', function (Publisher $publisher) {
return new Delete($publisher);
}, ['publisher']);
$setResource('queueForCertificates', function (Publisher $publisher) {
CLI::setResource('queueForCertificates', function (Publisher $publisher) {
return new Certificate($publisher);
}, ['publisher']);
$setResource('logError', function (Registry $register) {
CLI::setResource('logError', function (Registry $register) {
return function (Throwable $error, string $namespace, string $action) use ($register) {
Console::error('[Error] Timestamp: ' . date('c', time()));
Console::error('[Error] Type: ' . get_class($error));
@@ -293,14 +265,6 @@ $setResource('logError', function (Registry $register) {
$log->addExtra('trace', $error->getTraceAsString());
$log->addExtra('detailedTrace', $error->getTrace());
if ($error->getPrevious() !== null) {
if ($error->getPrevious()->getMessage() != $error->getMessage()) {
$log->addExtra('previousMessage', $error->getPrevious()->getMessage());
}
$log->addExtra('previousFile', $error->getPrevious()->getFile());
$log->addExtra('previousLine', $error->getPrevious()->getLine());
}
$log->setAction($action);
$isProduction = System::getEnv('_APP_ENV', 'development') === 'production';
@@ -316,9 +280,22 @@ $setResource('logError', function (Registry $register) {
};
}, ['register']);
$setResource('executor', fn () => new Executor(), []);
CLI::setResource('executor', fn () => new Executor());
$setResource('telemetry', fn () => new NoTelemetry(), []);
CLI::setResource('telemetry', fn () => new NoTelemetry());
$platform = new Appwrite();
$args = $platform->getEnv('argv');
if (!isset($args[0])) {
Console::error('Missing task name');
Console::exit(1);
}
\array_shift($args);
$taskName = $args[0];
$platform->init(Service::TYPE_TASK);
$cli = $platform->getCli();
$cli
->error()
@@ -337,5 +314,4 @@ $cli
$cli->shutdown()->action(fn () => Timer::clearAll());
Runtime::enableCoroutine(SWOOLE_HOOK_ALL);
require_once __DIR__ . '/init/span.php';
run($cli->run(...));
+2 -4
View File
@@ -4,7 +4,6 @@
$common = include __DIR__ . '/collections/common.php';
$projects = include __DIR__ . '/collections/projects.php';
$databases = include __DIR__ . '/collections/databases.php';
$vectordb = include __DIR__ . '/collections/vectordb.php';
$platform = include __DIR__ . '/collections/platform.php';
$logs = include __DIR__ . '/collections/logs.php';
@@ -27,9 +26,8 @@ unset($common['files']);
$collections = [
'buckets' => $buckets,
'databases' => $databases,
'vectordb' => $vectordb,
'projects' => array_merge_recursive($projects, $common),
'console' => array_merge_recursive($platform, $common),
'projects' => array_merge($projects, $common),
'console' => array_merge($platform, $common),
'logs' => $logs,
];
+21 -12
View File
@@ -1288,17 +1288,6 @@ return [
'array' => false,
'filters' => ['json'],
],
[
'$id' => ID::custom('labels'),
'type' => Database::VAR_STRING,
'format' => '',
'size' => 128,
'signed' => true,
'required' => false,
'default' => null,
'array' => true,
'filters' => [],
],
],
'indexes' => [
[
@@ -1617,6 +1606,13 @@ return [
],
],
'indexes' => [
[
'$id' => ID::custom('_fulltext_name'),
'type' => Database::INDEX_FULLTEXT,
'attributes' => ['name'],
'lengths' => [],
'orders' => [],
],
[
'$id' => ID::custom('_key_search'),
'type' => Database::INDEX_FULLTEXT,
@@ -1846,6 +1842,13 @@ return [
'lengths' => [],
'orders' => [Database::ORDER_ASC],
],
[
'$id' => ID::custom('_key_name'),
'type' => Database::INDEX_FULLTEXT,
'attributes' => ['name'],
'lengths' => [],
'orders' => [Database::ORDER_ASC],
],
[
'$id' => ID::custom('_key_type'),
'type' => Database::INDEX_KEY,
@@ -2113,8 +2116,14 @@ return [
'filters' => ['topicSearch'],
],
],
'indexes' => [
[
'$id' => ID::custom('_key_name'),
'type' => Database::INDEX_FULLTEXT,
'attributes' => ['name'],
'lengths' => [],
'orders' => [],
],
[
'$id' => ID::custom('_key_search'),
'type' => Database::INDEX_FULLTEXT,
+21 -82
View File
@@ -6,7 +6,7 @@ use Utopia\Database\Helpers\ID;
$providers = Config::getParam('oAuthProviders', []);
$platformCollections = [
return [
'projects' => [
'$collection' => ID::custom(Database::METADATA),
'$id' => ID::custom('projects'),
@@ -330,29 +330,7 @@ $platformCollections = [
'default' => null,
'array' => false,
'filters' => ['datetime'],
],
[
'$id' => ID::custom('labels'),
'type' => Database::VAR_STRING,
'format' => '',
'size' => 128,
'signed' => true,
'required' => false,
'default' => [],
'array' => true,
'filters' => [],
],
[
'$id' => 'status',
'type' => Database::VAR_STRING,
'format' => '',
'size' => 100,
'signed' => false,
'required' => false,
'default' => null,
'array' => false,
'filters' => [],
],
]
],
'indexes' => [
[
@@ -644,35 +622,24 @@ $platformCollections = [
'name' => 'keys',
'attributes' => [
[
'$id' => ID::custom('resourceType'),
'$id' => ID::custom('projectInternalId'),
'type' => Database::VAR_STRING,
'format' => '',
'size' => Database::LENGTH_KEY,
'signed' => true,
'required' => false,
'required' => true,
'default' => null,
'array' => false,
'filters' => [],
],
[
'$id' => ID::custom('resourceId'),
'$id' => ID::custom('projectId'),
'type' => Database::VAR_STRING,
'format' => '',
'size' => Database::LENGTH_KEY,
'signed' => true,
'required' => false,
'default' => null,
'array' => false,
'filters' => [],
],
[
'$id' => ID::custom('resourceInternalId'),
'type' => Database::VAR_STRING,
'format' => '',
'size' => Database::LENGTH_KEY,
'signed' => true,
'required' => false,
'default' => null,
'default' => 0,
'array' => false,
'filters' => [],
],
@@ -745,14 +712,14 @@ $platformCollections = [
],
'indexes' => [
[
'$id' => ID::custom('_key_resource'),
'$id' => ID::custom('_key_project'),
'type' => Database::INDEX_KEY,
'attributes' => ['resourceType', 'resourceInternalId'],
'lengths' => [],
'orders' => [],
'attributes' => ['projectInternalId'],
'lengths' => [Database::LENGTH_KEY],
'orders' => [Database::ORDER_ASC],
],
[
'$id' => ID::custom('_key_accessedAt'),
'$id' => '_key_accessedAt',
'type' => Database::INDEX_KEY,
'attributes' => ['accessedAt'],
'lengths' => [],
@@ -1395,21 +1362,21 @@ $platformCollections = [
'$id' => '_key_type',
'type' => Database::INDEX_KEY,
'attributes' => ['type'],
'lengths' => [],
'lengths' => [32],
'orders' => [Database::ORDER_ASC],
],
[
'$id' => '_key_trigger',
'type' => Database::INDEX_KEY,
'attributes' => ['trigger'],
'lengths' => [],
'lengths' => [32],
'orders' => [Database::ORDER_ASC],
],
[
'$id' => '_key_deploymentResourceType',
'type' => Database::INDEX_KEY,
'attributes' => ['deploymentResourceType'],
'lengths' => [],
'lengths' => [32],
'orders' => [Database::ORDER_ASC],
],
[
@@ -1451,20 +1418,20 @@ $platformCollections = [
'$id' => ID::custom('_key_owner'),
'type' => Database::INDEX_KEY,
'attributes' => ['owner'],
'lengths' => [],
'lengths' => [16],
'orders' => [Database::ORDER_ASC],
],
[
'$id' => ID::custom('_key_piid_diid_drt'),
'$id' => ID::custom('_key_region'),
'type' => Database::INDEX_KEY,
'attributes' => ['projectInternalId', 'deploymentInternalId', 'deploymentResourceType'],
'lengths' => [],
'orders' => [],
'attributes' => ['region'],
'lengths' => [16],
'orders' => [Database::ORDER_ASC],
],
[
'$id' => '_key_region_status_createdAt',
'$id' => ID::custom('_key_piid_riid_rt'),
'type' => Database::INDEX_KEY,
'attributes' => ['region', 'status', '$createdAt'],
'attributes' => ['projectInternalId', 'deploymentInternalId', 'deploymentResourceType'],
'lengths' => [],
'orders' => [],
],
@@ -1936,31 +1903,3 @@ $platformCollections = [
'indexes' => []
],
];
// Organization API keys subquery
$platformCollections['teams']['attributes'][] = [
'$id' => ID::custom('keys'),
'type' => Database::VAR_STRING,
'format' => '',
'size' => 16384,
'signed' => true,
'required' => false,
'default' => null,
'array' => false,
'filters' => ['subQueryOrganizationKeys'],
];
// Account API keys subquery
$platformCollections['users']['attributes'][] = [
'$id' => ID::custom('keys'),
'type' => Database::VAR_STRING,
'format' => '',
'size' => 16384,
'signed' => true,
'required' => false,
'default' => null,
'array' => false,
'filters' => ['subQueryAccountKeys'],
];
return $platformCollections;
-115
View File
@@ -61,15 +61,6 @@ return [
'array' => false,
'filters' => [],
],
[
'$id' => ID::custom('database'),
'type' => Database::VAR_STRING,
'size' => 128,
'required' => true,
'signed' => true,
'array' => false,
'filters' => [],
]
],
'indexes' => [
[
@@ -576,17 +567,6 @@ return [
'array' => false,
'filters' => [],
],
[
'$id' => ID::custom('deploymentRetention'),
'type' => Database::VAR_INTEGER,
'format' => '',
'size' => 0,
'signed' => true,
'required' => false,
'default' => 0,
'array' => false,
'filters' => [],
],
[
'$id' => ID::custom('deploymentInternalId'),
'type' => Database::VAR_STRING,
@@ -785,17 +765,6 @@ return [
'default' => null,
'filters' => [],
],
[
'array' => false,
'$id' => ID::custom('startCommand'),
'type' => Database::VAR_STRING,
'format' => '',
'size' => 20000,
'signed' => true,
'required' => false,
'default' => null,
'filters' => [],
],
[
'array' => false,
'$id' => ID::custom('specification'),
@@ -807,28 +776,6 @@ return [
'default' => APP_COMPUTE_SPECIFICATION_DEFAULT,
'filters' => [],
],
[
'array' => false,
'$id' => ID::custom('buildSpecification'),
'type' => Database::VAR_STRING,
'format' => '',
'size' => 128,
'signed' => false,
'required' => false,
'default' => APP_COMPUTE_SPECIFICATION_DEFAULT,
'filters' => [],
],
[
'array' => false,
'$id' => ID::custom('runtimeSpecification'),
'type' => Database::VAR_STRING,
'format' => '',
'size' => 128,
'signed' => false,
'required' => false,
'default' => APP_COMPUTE_SPECIFICATION_DEFAULT,
'filters' => [],
],
[
'$id' => ID::custom('scopes'),
'type' => Database::VAR_STRING,
@@ -1088,17 +1035,6 @@ return [
'default' => null,
'filters' => [],
],
[
'array' => false,
'$id' => ID::custom('startCommand'),
'type' => Database::VAR_STRING,
'format' => '',
'size' => 20000,
'signed' => true,
'required' => false,
'default' => null,
'filters' => [],
],
[
'$id' => ID::custom('fallbackFile'),
'type' => Database::VAR_STRING,
@@ -1110,17 +1046,6 @@ return [
'array' => false,
'filters' => [],
],
[
'$id' => ID::custom('deploymentRetention'),
'type' => Database::VAR_INTEGER,
'format' => '',
'size' => 0,
'signed' => true,
'required' => false,
'default' => 0,
'array' => false,
'filters' => [],
],
[
'$id' => ID::custom('deploymentInternalId'),
'type' => Database::VAR_STRING,
@@ -1275,28 +1200,6 @@ return [
'default' => APP_COMPUTE_SPECIFICATION_DEFAULT,
'filters' => [],
],
[
'array' => false,
'$id' => ID::custom('buildSpecification'),
'type' => Database::VAR_STRING,
'format' => '',
'size' => 128,
'signed' => false,
'required' => false,
'default' => APP_COMPUTE_SPECIFICATION_DEFAULT,
'filters' => [],
],
[
'array' => false,
'$id' => ID::custom('runtimeSpecification'),
'type' => Database::VAR_STRING,
'format' => '',
'size' => 128,
'signed' => false,
'required' => false,
'default' => APP_COMPUTE_SPECIFICATION_DEFAULT,
'filters' => [],
],
[
'$id' => ID::custom('buildRuntime'),
'type' => Database::VAR_STRING,
@@ -1454,17 +1357,6 @@ return [
'default' => null,
'filters' => [],
],
[
'array' => false,
'$id' => ID::custom('startCommand'),
'type' => Database::VAR_STRING,
'format' => '',
'size' => 20000,
'signed' => true,
'required' => false,
'default' => null,
'filters' => [],
],
[
'array' => false,
'$id' => ID::custom('buildOutput'),
@@ -2206,13 +2098,6 @@ return [
'lengths' => [],
'orders' => [],
],
[
'$id' => ID::custom('_key_resourceType'),
'type' => Database::INDEX_KEY,
'attributes' => ['resourceType'],
'lengths' => [],
'orders' => [Database::ORDER_ASC],
],
],
],
-165
View File
@@ -1,165 +0,0 @@
<?php
use Utopia\Database\Database;
use Utopia\Database\Helpers\ID;
return [
'collections' => [
'$collection' => ID::custom('databases'),
'$id' => ID::custom('collections'),
'name' => 'Collections',
'attributes' => [
[
'$id' => ID::custom('databaseInternalId'),
'type' => Database::VAR_STRING,
'format' => '',
'size' => Database::LENGTH_KEY,
'signed' => true,
'required' => true,
'default' => null,
'array' => false,
'filters' => [],
],
[
'$id' => ID::custom('databaseId'),
'type' => Database::VAR_STRING,
'signed' => true,
'size' => Database::LENGTH_KEY,
'format' => '',
'filters' => [],
'required' => true,
'default' => null,
'array' => false,
],
[
'$id' => ID::custom('name'),
'type' => Database::VAR_STRING,
'size' => 256,
'required' => true,
'signed' => true,
'array' => false,
'filters' => [],
],
[
'$id' => ID::custom('dimension'),
'type' => Database::VAR_INTEGER,
'size' => 0,
'required' => true,
'signed' => false,
'array' => false,
'filters' => [],
],
[
'$id' => ID::custom('enabled'),
'type' => Database::VAR_BOOLEAN,
'signed' => true,
'size' => 0,
'format' => '',
'filters' => [],
'required' => true,
'default' => null,
'array' => false,
],
[
'$id' => ID::custom('documentSecurity'),
'type' => Database::VAR_BOOLEAN,
'signed' => true,
'size' => 0,
'format' => '',
'filters' => [],
'required' => true,
'default' => null,
'array' => false,
],
[
'$id' => ID::custom('attributes'),
'type' => Database::VAR_STRING,
'size' => 1000000,
'required' => false,
'signed' => true,
'array' => false,
'filters' => ['subQueryAttributes'],
],
[
'$id' => ID::custom('indexes'),
'type' => Database::VAR_STRING,
'size' => 1000000,
'required' => false,
'signed' => true,
'array' => false,
'filters' => ['subQueryIndexes'],
],
[
'$id' => ID::custom('search'),
'type' => Database::VAR_STRING,
'format' => '',
'size' => 16384,
'signed' => true,
'required' => false,
'default' => null,
'array' => false,
'filters' => [],
],
],
'defaultAttributes' => [
[
'$id' => ID::custom('embeddings'),
'type' => Database::VAR_VECTOR,
'required' => true,
'signed' => false,
'array' => false,
'filters' => [],
],
[
'$id' => ID::custom('metadata'),
'type' => Database::VAR_OBJECT,
'default' => [],
'required' => false,
'size' => 0,
'signed' => false,
'array' => false,
'filters' => [],
],
],
'indexes' => [
[
'$id' => ID::custom('_fulltext_search'),
'type' => Database::INDEX_FULLTEXT,
'attributes' => ['search'],
'lengths' => [],
'orders' => [],
],
[
'$id' => ID::custom('_key_name'),
'type' => Database::INDEX_KEY,
'attributes' => ['name'],
'lengths' => [256],
'orders' => [Database::ORDER_ASC],
],
[
'$id' => ID::custom('_key_enabled'),
'type' => Database::INDEX_KEY,
'attributes' => ['enabled'],
'lengths' => [],
'orders' => [Database::ORDER_ASC],
],
[
'$id' => ID::custom('_key_documentSecurity'),
'type' => Database::INDEX_KEY,
'attributes' => ['documentSecurity'],
'lengths' => [],
'orders' => [Database::ORDER_ASC],
],
],
'defaultIndexes' => [
// not creating default indexes on the embeddings as it depends on the type of query users using the most
[
'$id' => ID::custom('_key_metadata'),
'type' => Database::INDEX_OBJECT,
'attributes' => ['metadata'],
'lengths' => [],
'orders' => [],
],
]
]
];
-53
View File
@@ -1,53 +0,0 @@
<?php
/**
* CORS Configuration
*
* Centralised list of allowed methods, headers, and exposed headers for CORS responses.
*/
return [
'allowedMethods' => ['GET', 'POST', 'PUT', 'PATCH', 'DELETE'],
'allowedHeaders' => [
'Accept',
'Origin',
'Cookie',
'Set-Cookie',
// Content
'Content-Type',
'Content-Range',
// Appwrite
'X-Appwrite-Project',
'X-Appwrite-Key',
'X-Appwrite-Dev-Key',
'X-Appwrite-Locale',
'X-Appwrite-Mode',
'X-Appwrite-JWT',
'X-Appwrite-Response-Format',
'X-Appwrite-Timeout',
'X-Appwrite-ID',
'X-Appwrite-Timestamp',
'X-Appwrite-Session',
'X-Appwrite-Platform',
// SDK generator
'X-SDK-Version',
'X-SDK-Name',
'X-SDK-Language',
'X-SDK-Platform',
'X-SDK-GraphQL',
'X-SDK-Profile',
// Caching
'Range',
'Cache-Control',
'Expires',
'Pragma',
// Server to server
'X-Fallback-Cookies',
'X-Requested-With',
'X-Forwarded-For',
'X-Forwarded-User-Agent',
],
'exposedHeaders' => [
'X-Appwrite-Session',
'X-Fallback-Cookies',
],
];
+1 -30
View File
@@ -357,11 +357,6 @@ return [
'description' => 'API key and session used in the same request. Use either `setSession` or `setKey`. Learn about which authentication method to use in the SSR docs: https://appwrite.io/docs/products/auth/server-side-rendering',
'code' => 403,
],
Exception::USER_JWT_AND_COOKIE_SET => [
'name' => Exception::USER_JWT_AND_COOKIE_SET,
'description' => 'JWT and cookie used in the same request. Use either `setJWT` or `setCookie`. Learn about which authentication method to use in the SSR docs: https://appwrite.io/docs/products/auth/server-side-rendering',
'code' => 403,
],
Exception::API_KEY_EXPIRED => [
'name' => Exception::API_KEY_EXPIRED,
'description' => 'The dynamic API key has expired. Please don\'t use dynamic API keys for more than duration of the execution.',
@@ -1079,11 +1074,6 @@ return [
'description' => 'The project key has expired. Please generate a new key using the Appwrite console.',
'code' => 401,
],
Exception::ACCOUNT_KEY_EXPIRED => [
'name' => Exception::ACCOUNT_KEY_EXPIRED,
'description' => 'The account API key has expired. Please generate a new key using the Appwrite console.',
'code' => 401,
],
Exception::ROUTER_HOST_NOT_FOUND => [
'name' => Exception::ROUTER_HOST_NOT_FOUND,
'description' => 'Host is not trusted. This could occur because you have not configured a custom domain. Add a custom domain to your project first and try again.',
@@ -1113,6 +1103,7 @@ return [
'name' => Exception::RULE_VERIFICATION_FAILED,
'description' => 'Domain verification failed. Please check if your DNS records are correct and try again.',
'code' => 400,
'publish' => true
],
Exception::PROJECT_SMTP_CONFIG_INVALID => [
'name' => Exception::PROJECT_SMTP_CONFIG_INVALID,
@@ -1139,11 +1130,6 @@ return [
'description' => 'Key with the requested ID could not be found.',
'code' => 404,
],
Exception::KEY_ALREADY_EXISTS => [
'name' => Exception::KEY_ALREADY_EXISTS,
'description' => 'Key with the same ID already exists. Try again with a different ID.',
'code' => 409,
],
Exception::PLATFORM_NOT_FOUND => [
'name' => Exception::PLATFORM_NOT_FOUND,
'description' => 'Platform with the requested ID could not be found.',
@@ -1343,19 +1329,4 @@ return [
'description' => 'Target has an invalid provider type.',
'code' => 400,
],
Exception::USER_ID_MISSING => [
'name' => Exception::USER_ID_MISSING,
'description' => 'When using account API key, make sure to pass x-appwrite-user header with your user ID.',
'code' => 403,
],
Exception::ORGANIZATION_ID_MISSING => [
'name' => Exception::ORGANIZATION_ID_MISSING,
'description' => 'When using organization API key, make sure to pass x-appwrite-organization header with your organization ID.',
'code' => 403,
],
Exception::PROJECT_ID_MISSING => [
'name' => Exception::PROJECT_ID_MISSING,
'description' => 'When using project API key, make sure to pass x-appwrite-project header with your project ID.',
'code' => 403,
],
];
-8
View File
@@ -405,14 +405,6 @@ return [
'$description' => 'This event triggers when a provider is deleted.'
],
],
'schedules' => [
'$model' => Response::MODEL_SCHEDULE,
'$resource' => true,
'$description' => 'This event triggers on any schedule event.',
'create' => [
'$description' => 'This event triggers when a schedule is created.',
],
],
'rules' => [
'$model' => Response::MODEL_PROXY_RULE,
'$resource' => true,
+38 -21
View File
@@ -50,12 +50,17 @@
font-style: normal;
font-display: swap;
}
@font-face {
font-family: 'Poppins';
src: url('https://assets.appwrite.io/fonts/poppins/poppins-v23-latin-regular.woff2') format('woff2');
font-weight: 400;
font-style: normal;
font-display: swap;
}
</style>
<style>
.main {
max-width: 650px;
margin: 0 auto;
margin-top: 32px;
body {
padding: 32px;
line-height: 1.5;
color: #616b7c;
@@ -63,12 +68,15 @@
font-weight: 400;
font-family: "Inter", sans-serif;
background-color: #ffffff;
margin: 0;
padding: 0;
line-height: 150%;
}
.main a {
a {
color: currentColor;
word-break: break-all;
}
.main a.button {
a.button {
box-sizing: border-box;
display: inline-block;
text-align: center;
@@ -79,8 +87,8 @@
border: 1px solid #414146;
border-radius: 8px;
}
.main a.button:hover,
.main a.button:focus {
a.button:hover,
a.button:focus {
opacity: 0.8;
}
table {
@@ -94,6 +102,11 @@
td {
vertical-align: top;
}
.main {
max-width: 650px;
margin: 0 auto;
margin-top: 32px;
}
h1 {
font-size: 22px;
margin-bottom: 0px;
@@ -125,6 +138,9 @@
border: none;
border-top: 1px solid #e8e9f0;
}
h* {
font-family: 'Poppins', sans-serif;
}
p {
margin-bottom: 10px;
}
@@ -139,20 +155,21 @@
<body style="direction: {{direction}}">
<div style="display: none; overflow: hidden; max-height: 0; max-width: 0; opacity: 0; line-height: 1px;">
{{preview}}
<div>{{previewWhitespace}}</div>
</div>
<div style="display: none; overflow: hidden; max-height: 0; max-width: 0; opacity: 0; line-height: 1px;">
{{preview}}
<div>{{previewWhitespace}}</div>
</div>
<div class="main" style="max-width:650px; word-wrap: break-word; overflow-wrap: break-word; word-break: normal; margin:0 auto;">
<table style="margin-top: 32px">
<tr>
<td>
{{body}}
</td>
</tr>
</table>
</div>
<div style="max-width:650px; word-wrap: break-word; overflow-wrap: break-word;
word-break: normal; margin:0 auto;">
<table style="margin-top: 32px">
<tr>
<td>
{{body}}
</td>
</tr>
</table>
</div>
</body>
</html>
-14
View File
@@ -2,17 +2,6 @@
use Utopia\System\System;
// For now, take first domain as primary (for previews)
// Later-on this can become platform-specific with new env var (appwrite=this,imagine=that)
$sitesDomain = System::getEnv('_APP_DOMAIN_SITES', '');
if (\str_contains($sitesDomain, ',')) {
$sitesDomain = explode(',', $sitesDomain)[0];
}
$functionsDomain = System::getEnv('_APP_DOMAIN_FUNCTIONS', '');
if (\str_contains($functionsDomain, ',')) {
$functionsDomain = explode(',', $functionsDomain)[0];
}
/**
* Platform configuration
*/
@@ -22,7 +11,6 @@ return [
'hostnames' => array_filter(array_unique([
System::getEnv('_APP_DOMAIN', 'localhost'),
System::getEnv('_APP_CONSOLE_DOMAIN', 'localhost'),
System::getEnv('_APP_MIGRATION_HOST'),
])),
'platformName' => APP_EMAIL_PLATFORM_NAME,
'logoUrl' => APP_EMAIL_LOGO_URL,
@@ -35,6 +23,4 @@ return [
'privacyUrl' => APP_EMAIL_PRIVACY_URL,
'websiteUrl' => 'https://' . APP_DOMAIN,
'emailSenderName' => APP_EMAIL_PLATFORM_NAME,
'sitesDomain' => $sitesDomain,
'functionsDomain' => $functionsDomain,
];
-2
View File
@@ -91,8 +91,6 @@ $admins = [
'subscribers.read',
'tokens.read',
'tokens.write',
'schedules.read',
'schedules.write',
];
return [
@@ -145,12 +145,6 @@ return [ // List of publicly visible scopes
'rules.write' => [
'description' => 'Access to create, update, and delete your project\'s proxy rules',
],
'schedules.read' => [
'description' => 'Access to read your project\'s schedules',
],
'schedules.write' => [
'description' => 'Access to create, update, and delete your project\'s schedules',
],
'migrations.read' => [
'description' => 'Access to read your project\'s migrations',
],
-15
View File
@@ -1,15 +0,0 @@
<?php
// List of scopes for Account API keys (Tokens)
return [
"account" => [
"description" => 'Access to manage account, its organizations, sessions, tokens, and billing.',
],
"teams.read" => [
"description" => 'Access to read account\'s organizations.',
],
"teams.write" => [
"description" => 'Access to create, update and delete account\'s organizations and its memberships.',
],
];
-42
View File
@@ -1,42 +0,0 @@
<?php
// List of scopes for organization (teams) API keys
return [
"platforms.read" => [
"description" => 'Access to read project\'s platforms',
],
"platforms.write" => [
"description" =>
'Access to create, update, and delete project\'s platforms',
],
"projects.read" => [
"description" => 'Access to read organization\'s projects',
],
"projects.write" => [
"description" =>
"Access to create, update, and delete projects in organization",
],
"keys.read" => [
"description" => 'Access to read project\'s API keys',
],
"keys.write" => [
"description" =>
"Access to create, update, and delete project\'s API keys",
],
"devKeys.read" => [
"description" => 'Access to read project\'s development keys',
],
"devKeys.write" => [
"description" =>
"Access to create, update, and delete project\'s development keys",
],
"webhooks.read" => [
"description" =>
"Access to read project\'s webhooks",
],
"webhooks.write" => [
"description" =>
"Access to create, update, and delete project\'s webhooks",
],
];
+16 -57
View File
@@ -11,7 +11,7 @@ return [
[
'key' => 'web',
'name' => 'Web',
'version' => '22.4.0',
'version' => '21.5.0',
'url' => 'https://github.com/appwrite/sdk-for-web',
'package' => 'https://www.npmjs.com/package/appwrite',
'enabled' => true,
@@ -60,7 +60,7 @@ return [
[
'key' => 'flutter',
'name' => 'Flutter',
'version' => '21.4.0',
'version' => '20.3.2',
'url' => 'https://github.com/appwrite/sdk-for-flutter',
'package' => 'https://pub.dev/packages/appwrite',
'enabled' => true,
@@ -79,7 +79,7 @@ return [
[
'key' => 'apple',
'name' => 'Apple',
'version' => '14.3.0',
'version' => '13.5.0',
'url' => 'https://github.com/appwrite/sdk-for-apple',
'package' => 'https://github.com/appwrite/sdk-for-apple',
'enabled' => true,
@@ -116,8 +116,7 @@ return [
[
'key' => 'android',
'name' => 'Android',
'namespace' => 'io.appwrite',
'version' => '12.2.0',
'version' => '11.4.0',
'url' => 'https://github.com/appwrite/sdk-for-android',
'package' => 'https://search.maven.org/artifact/io.appwrite/sdk-for-android',
'enabled' => true,
@@ -140,7 +139,7 @@ return [
[
'key' => 'react-native',
'name' => 'React Native',
'version' => '0.24.0',
'version' => '0.19.0',
'url' => 'https://github.com/appwrite/sdk-for-react-native',
'package' => 'https://npmjs.com/package/react-native-appwrite',
'enabled' => true,
@@ -208,7 +207,7 @@ return [
[
'key' => 'web',
'name' => 'Console',
'version' => '22.4.0',
'version' => '0.2.0',
'url' => '',
'package' => '',
'enabled' => true,
@@ -227,7 +226,7 @@ return [
[
'key' => 'cli',
'name' => 'Command Line',
'version' => '13.5.0',
'version' => '12.0.1',
'url' => 'https://github.com/appwrite/sdk-for-cli',
'package' => 'https://www.npmjs.com/package/appwrite-cli',
'enabled' => true,
@@ -250,45 +249,6 @@ return [
],
],
],
[
'key' => 'markdown',
'name' => 'Markdown',
'version' => '0.3.0',
'url' => 'https://github.com/appwrite/sdk-for-md.git',
'package' => 'https://www.npmjs.com/package/@appwrite.io/docs',
'enabled' => true,
'beta' => false,
'dev' => false,
'hidden' => false,
'family' => APP_SDK_PLATFORM_CONSOLE,
'prism' => 'markdown',
'source' => \realpath(__DIR__ . '/../sdks/console-md'),
'gitUrl' => 'git@github.com:appwrite/sdk-for-md.git',
'gitRepoName' => 'sdk-for-md',
'gitUserName' => 'appwrite',
'gitBranch' => 'dev',
'repoBranch' => 'main',
'changelog' => \realpath(__DIR__ . '/../../docs/sdks/md/CHANGELOG.md'),
],
[
'key' => 'agent-skills',
'name' => 'AgentSkills',
'version' => '0.1.0',
'url' => 'https://github.com/appwrite/agent-skills.git',
'enabled' => true,
'beta' => false,
'dev' => false,
'hidden' => false,
'family' => APP_SDK_PLATFORM_CONSOLE,
'prism' => 'agent-skills',
'source' => \realpath(__DIR__ . '/../sdks/console-agent-skills'),
'gitUrl' => 'git@github.com:appwrite/agent-skills.git',
'gitRepoName' => 'agent-skills',
'gitUserName' => 'appwrite',
'gitBranch' => 'dev',
'repoBranch' => 'main',
'changelog' => \realpath(__DIR__ . '/../../docs/sdks/agent-skills/CHANGELOG.md'),
],
],
],
@@ -302,7 +262,7 @@ return [
[
'key' => 'nodejs',
'name' => 'Node.js',
'version' => '22.0.1',
'version' => '21.1.0',
'url' => 'https://github.com/appwrite/sdk-for-node',
'package' => 'https://www.npmjs.com/package/node-appwrite',
'enabled' => true,
@@ -321,7 +281,7 @@ return [
[
'key' => 'php',
'name' => 'PHP',
'version' => '20.0.1',
'version' => '19.1.0',
'url' => 'https://github.com/appwrite/sdk-for-php',
'package' => 'https://packagist.org/packages/appwrite/appwrite',
'enabled' => true,
@@ -340,7 +300,7 @@ return [
[
'key' => 'python',
'name' => 'Python',
'version' => '15.1.0',
'version' => '14.1.0',
'url' => 'https://github.com/appwrite/sdk-for-python',
'package' => 'https://pypi.org/project/appwrite/',
'enabled' => true,
@@ -359,7 +319,7 @@ return [
[
'key' => 'ruby',
'name' => 'Ruby',
'version' => '21.0.1',
'version' => '20.1.0',
'url' => 'https://github.com/appwrite/sdk-for-ruby',
'package' => 'https://rubygems.org/gems/appwrite',
'enabled' => true,
@@ -378,7 +338,7 @@ return [
[
'key' => 'go',
'name' => 'Go',
'version' => 'v0.16.1',
'version' => 'v0.16.0',
'url' => 'https://github.com/appwrite/sdk-for-go',
'package' => 'https://github.com/appwrite/sdk-for-go',
'enabled' => true,
@@ -397,7 +357,7 @@ return [
[
'key' => 'dotnet',
'name' => '.NET',
'version' => '0.26.0',
'version' => '0.24.0',
'url' => 'https://github.com/appwrite/sdk-for-dotnet',
'package' => 'https://www.nuget.org/packages/Appwrite',
'enabled' => true,
@@ -416,7 +376,7 @@ return [
[
'key' => 'dart',
'name' => 'Dart',
'version' => '21.0.1',
'version' => '20.1.0',
'url' => 'https://github.com/appwrite/sdk-for-dart',
'package' => 'https://pub.dev/packages/dart_appwrite',
'enabled' => true,
@@ -435,8 +395,7 @@ return [
[
'key' => 'kotlin',
'name' => 'Kotlin',
'namespace' => 'io.appwrite',
'version' => '14.0.1',
'version' => '13.1.0',
'url' => 'https://github.com/appwrite/sdk-for-kotlin',
'package' => 'https://search.maven.org/artifact/io.appwrite/sdk-for-kotlin',
'enabled' => true,
@@ -459,7 +418,7 @@ return [
[
'key' => 'swift',
'name' => 'Swift',
'version' => '15.1.0',
'version' => '14.1.0',
'url' => 'https://github.com/appwrite/sdk-for-swift',
'package' => 'https://github.com/appwrite/sdk-for-swift',
'enabled' => true,
+6 -6
View File
@@ -20,7 +20,7 @@ return [
'name' => 'Console',
'subtitle' => '',
'description' => '',
'controller' => '', // Uses modules
'controller' => 'web/console.php',
'sdk' => false,
'docs' => false,
'docsUrl' => '',
@@ -48,7 +48,7 @@ return [
'name' => 'Avatars',
'subtitle' => 'The Avatars service aims to help you complete everyday tasks related to your app image, icons, and avatars.',
'description' => '/docs/services/avatars.md',
'controller' => '', // Uses modules
'controller' => 'api/avatars.php',
'sdk' => true,
'docs' => true,
'docsUrl' => 'https://appwrite.io/docs/client/avatars',
@@ -104,7 +104,7 @@ return [
'name' => 'Health',
'subtitle' => 'The Health service allows you to both validate and monitor your Appwrite server\'s health.',
'description' => '/docs/services/health.md',
'controller' => '', // Uses modules
'controller' => 'api/health.php',
'sdk' => true,
'docs' => true,
'docsUrl' => 'https://appwrite.io/docs/server/health',
@@ -146,7 +146,7 @@ return [
'name' => 'Storage',
'subtitle' => 'The Storage service allows you to manage your project files.',
'description' => '/docs/services/storage.md',
'controller' => '', // Uses modules
'controller' => 'api/storage.php',
'sdk' => true,
'docs' => true,
'docsUrl' => 'https://appwrite.io/docs/client/storage',
@@ -270,9 +270,9 @@ return [
'console' => [
'key' => 'console',
'name' => 'Console',
'subtitle' => 'The Console service allows you to interact with console relevant information.',
'subtitle' => 'The Console service allows you to interact with console relevant informations.',
'description' => '',
'controller' => '', // Uses modules
'controller' => 'api/console.php',
'sdk' => true,
'docs' => true,
'docsUrl' => '',
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because it is too large Load Diff
File diff suppressed because it is too large Load Diff
File diff suppressed because it is too large Load Diff
File diff suppressed because it is too large Load Diff
File diff suppressed because it is too large Load Diff
File diff suppressed because it is too large Load Diff
File diff suppressed because it is too large Load Diff
File diff suppressed because it is too large Load Diff
File diff suppressed because it is too large Load Diff
File diff suppressed because it is too large Load Diff
File diff suppressed because it is too large Load Diff
File diff suppressed because it is too large Load Diff
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long

Some files were not shown because too many files have changed in this diff Show More