Compare commits
133 Commits
fix/imessa
...
fix/openco
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
7b31689346 | ||
|
|
b88e32083d | ||
|
|
6c42d34610 | ||
|
|
ee1ec3faba | ||
|
|
a459e237e8 | ||
|
|
47538bca4d | ||
|
|
05b28c147d | ||
|
|
0a48592475 | ||
|
|
3ad7958365 | ||
|
|
34a58b839c | ||
|
|
ec0728b357 | ||
|
|
0c7fa2b0d5 | ||
|
|
5f6e1c19bd | ||
|
|
7e005acd3c | ||
|
|
8ba1387ba2 | ||
|
|
7e32f1ce20 | ||
|
|
2267d58afc | ||
|
|
02842bef91 | ||
|
|
57326f72e6 | ||
|
|
370bbcd89b | ||
|
|
6f4665dda3 | ||
|
|
2d15dd757d | ||
|
|
861725fba1 | ||
|
|
de7b2ba7d5 | ||
|
|
7db839544d | ||
|
|
5958e5693c | ||
|
|
bc88e58fcf | ||
|
|
141f551a4c | ||
|
|
6ff209e932 | ||
|
|
b0befb5f5d | ||
|
|
40e23b05f7 | ||
|
|
313e2f2e85 | ||
|
|
68393bfa36 | ||
|
|
155dfa93e5 | ||
|
|
db31c0ccca | ||
|
|
cefd87f355 | ||
|
|
8577d015b2 | ||
|
|
4a5e9f0a4f | ||
|
|
c18452598a | ||
|
|
3299aeb904 | ||
|
|
8fdc0a2841 | ||
|
|
873182ec2d | ||
|
|
b8004a28cc | ||
|
|
6b7d3c3062 | ||
|
|
d4c560853c | ||
|
|
4e1a7cd60c | ||
|
|
4629054403 | ||
|
|
93b450349f | ||
|
|
2ca78a8aed | ||
|
|
db8e9b37c6 | ||
|
|
ad13c265ba | ||
|
|
7159d3b254 | ||
|
|
d6c088910b | ||
|
|
821520a057 | ||
|
|
f32eeae3bc | ||
|
|
7c951b01ab | ||
|
|
4fc4c5256a | ||
|
|
eb80b9acb3 | ||
|
|
ea237115a9 | ||
|
|
679bb087db | ||
|
|
1473fb19a5 | ||
|
|
01db1dde1a | ||
|
|
a13efbe2b5 | ||
|
|
6ac5dd2c0e | ||
|
|
eef247b7a4 | ||
|
|
9e0030b75f | ||
|
|
ddedb56c01 | ||
|
|
547374220c | ||
|
|
c8f4bca0c4 | ||
|
|
3011b00d39 | ||
|
|
cf95b2f3f4 | ||
|
|
203e3804b3 | ||
|
|
34424ce536 | ||
|
|
675c26b2b0 | ||
|
|
8b8451231c | ||
|
|
460808e0c8 | ||
|
|
f2c5c847bd | ||
|
|
c0b267a03a | ||
|
|
8860d2ed7f | ||
|
|
a4d1af1b11 | ||
|
|
5031b283a5 | ||
|
|
bdb90ea4ee | ||
|
|
d6cde28c8e | ||
|
|
f26cc60872 | ||
|
|
1ee1522daa | ||
|
|
34e78a7054 | ||
|
|
44bbe09bee | ||
|
|
1008c28f5a | ||
|
|
0621d0e9e8 | ||
|
|
3b40227bc6 | ||
|
|
d84eb46467 | ||
|
|
8524666454 | ||
|
|
54ddbc4660 | ||
|
|
7f95cdac78 | ||
|
|
cfdc551346 | ||
|
|
f895c9fba1 | ||
|
|
22927b0834 | ||
|
|
385a7eba33 | ||
|
|
a6fd76efeb | ||
|
|
21f8c3db18 | ||
|
|
392bbddf29 | ||
|
|
0cd47d830f | ||
|
|
90b4e54354 | ||
|
|
4434cae565 | ||
|
|
5e025c4ba3 | ||
|
|
a13ff55bd9 | ||
|
|
96abc1c864 | ||
|
|
38e6da1fe0 | ||
|
|
a42e3cb78a | ||
|
|
bebf323775 | ||
|
|
5d82c82313 | ||
|
|
43590d8287 | ||
|
|
dae0e2b325 | ||
|
|
3e14192730 | ||
|
|
dbaf0a8ae2 | ||
|
|
5bd63b012c | ||
|
|
3fae903863 | ||
|
|
d5f8208c38 | ||
|
|
42c690632d | ||
|
|
1d17630dc6 | ||
|
|
2b1da4f5d8 | ||
|
|
aaeecc8c8d | ||
|
|
eab0a07f71 | ||
|
|
01ce144fa9 | ||
|
|
718dba8cb6 | ||
|
|
9822985ea6 | ||
|
|
2196456d4a | ||
|
|
6f200ea77f | ||
|
|
5b0851ebd8 | ||
|
|
19ecdce275 | ||
|
|
18652d181b | ||
|
|
f633a8cb22 | ||
|
|
78f8a29071 |
185
.agents/skills/merge-pr/SKILL.md
Normal file
185
.agents/skills/merge-pr/SKILL.md
Normal file
@@ -0,0 +1,185 @@
|
||||
---
|
||||
name: merge-pr
|
||||
description: Merge a GitHub PR via squash after /preparepr. Use when asked to merge a ready PR. Do not push to main or modify code. Ensure the PR ends in MERGED state and clean up worktrees after success.
|
||||
---
|
||||
|
||||
# Merge PR
|
||||
|
||||
## Overview
|
||||
|
||||
Merge a prepared PR via `gh pr merge --squash` and clean up the worktree after success.
|
||||
|
||||
## Inputs
|
||||
|
||||
- Ask for PR number or URL.
|
||||
- If missing, auto-detect from conversation.
|
||||
- If ambiguous, ask.
|
||||
|
||||
## Safety
|
||||
|
||||
- Use `gh pr merge --squash` as the only path to `main`.
|
||||
- Do not run `git push` at all during merge.
|
||||
- Do not run gateway stop commands. Do not kill processes. Do not touch port 18792.
|
||||
|
||||
## Execution Rule
|
||||
|
||||
- Execute the workflow. Do not stop after printing the TODO checklist.
|
||||
- If delegating, require the delegate to run commands and capture outputs.
|
||||
|
||||
## Known Footguns
|
||||
|
||||
- If you see "fatal: not a git repository", you are in the wrong directory. Use `~/Development/openclaw`, not `~/openclaw`.
|
||||
- Read `.local/review.md` and `.local/prep.md` in the worktree. Do not skip.
|
||||
- Clean up the real worktree directory `.worktrees/pr-<PR>` only after a successful merge.
|
||||
- Expect cleanup to remove `.local/` artifacts.
|
||||
|
||||
## Completion Criteria
|
||||
|
||||
- Ensure `gh pr merge` succeeds.
|
||||
- Ensure PR state is `MERGED`, never `CLOSED`.
|
||||
- Record the merge SHA.
|
||||
- Run cleanup only after merge success.
|
||||
|
||||
## First: Create a TODO Checklist
|
||||
|
||||
Create a checklist of all merge steps, print it, then continue and execute the commands.
|
||||
|
||||
## Setup: Use a Worktree
|
||||
|
||||
Use an isolated worktree for all merge work.
|
||||
|
||||
```sh
|
||||
cd ~/Development/openclaw
|
||||
# Sanity: confirm you are in the repo
|
||||
git rev-parse --show-toplevel
|
||||
|
||||
WORKTREE_DIR=".worktrees/pr-<PR>"
|
||||
```
|
||||
|
||||
Run all commands inside the worktree directory.
|
||||
|
||||
## Load Local Artifacts (Mandatory)
|
||||
|
||||
Expect these files from earlier steps:
|
||||
|
||||
- `.local/review.md` from `/reviewpr`
|
||||
- `.local/prep.md` from `/preparepr`
|
||||
|
||||
```sh
|
||||
ls -la .local || true
|
||||
|
||||
if [ -f .local/review.md ]; then
|
||||
echo "Found .local/review.md"
|
||||
sed -n '1,120p' .local/review.md
|
||||
else
|
||||
echo "Missing .local/review.md. Stop and run /reviewpr, then /preparepr."
|
||||
exit 1
|
||||
fi
|
||||
|
||||
if [ -f .local/prep.md ]; then
|
||||
echo "Found .local/prep.md"
|
||||
sed -n '1,120p' .local/prep.md
|
||||
else
|
||||
echo "Missing .local/prep.md. Stop and run /preparepr first."
|
||||
exit 1
|
||||
fi
|
||||
```
|
||||
|
||||
## Steps
|
||||
|
||||
1. Identify PR meta
|
||||
|
||||
```sh
|
||||
gh pr view <PR> --json number,title,state,isDraft,author,headRefName,baseRefName,headRepository,body --jq '{number,title,state,isDraft,author:.author.login,head:.headRefName,base:.baseRefName,headRepo:.headRepository.nameWithOwner,body}'
|
||||
contrib=$(gh pr view <PR> --json author --jq .author.login)
|
||||
head=$(gh pr view <PR> --json headRefName --jq .headRefName)
|
||||
head_repo_url=$(gh pr view <PR> --json headRepository --jq .headRepository.url)
|
||||
```
|
||||
|
||||
2. Run sanity checks
|
||||
|
||||
Stop if any are true:
|
||||
|
||||
- PR is a draft.
|
||||
- Required checks are failing.
|
||||
- Branch is behind main.
|
||||
|
||||
```sh
|
||||
# Checks
|
||||
gh pr checks <PR>
|
||||
|
||||
# Check behind main
|
||||
git fetch origin main
|
||||
git fetch origin pull/<PR>/head:pr-<PR>
|
||||
git merge-base --is-ancestor origin/main pr-<PR> || echo "PR branch is behind main, run /preparepr"
|
||||
```
|
||||
|
||||
If anything is failing or behind, stop and say to run `/preparepr`.
|
||||
|
||||
3. Merge PR and delete branch
|
||||
|
||||
If checks are still running, use `--auto` to queue the merge.
|
||||
|
||||
```sh
|
||||
# Check status first
|
||||
check_status=$(gh pr checks <PR> 2>&1)
|
||||
if echo "$check_status" | grep -q "pending\|queued"; then
|
||||
echo "Checks still running, using --auto to queue merge"
|
||||
gh pr merge <PR> --squash --delete-branch --auto
|
||||
echo "Merge queued. Monitor with: gh pr checks <PR> --watch"
|
||||
else
|
||||
gh pr merge <PR> --squash --delete-branch
|
||||
fi
|
||||
```
|
||||
|
||||
If merge fails, report the error and stop. Do not retry in a loop.
|
||||
If the PR needs changes beyond what `/preparepr` already did, stop and say to run `/preparepr` again.
|
||||
|
||||
4. Get merge SHA
|
||||
|
||||
```sh
|
||||
merge_sha=$(gh pr view <PR> --json mergeCommit --jq '.mergeCommit.oid')
|
||||
echo "merge_sha=$merge_sha"
|
||||
```
|
||||
|
||||
5. Optional comment
|
||||
|
||||
Use a literal multiline string or heredoc for newlines.
|
||||
|
||||
```sh
|
||||
gh pr comment <PR> -F - <<'EOF'
|
||||
Merged via squash.
|
||||
|
||||
- Merge commit: $merge_sha
|
||||
|
||||
Thanks @$contrib!
|
||||
EOF
|
||||
```
|
||||
|
||||
6. Verify PR state is MERGED
|
||||
|
||||
```sh
|
||||
gh pr view <PR> --json state --jq .state
|
||||
```
|
||||
|
||||
7. Clean up worktree only on success
|
||||
|
||||
Run cleanup only if step 6 returned `MERGED`.
|
||||
|
||||
```sh
|
||||
cd ~/Development/openclaw
|
||||
|
||||
git worktree remove ".worktrees/pr-<PR>" --force
|
||||
|
||||
git branch -D temp/pr-<PR> 2>/dev/null || true
|
||||
git branch -D pr-<PR> 2>/dev/null || true
|
||||
```
|
||||
|
||||
## Guardrails
|
||||
|
||||
- Worktree only.
|
||||
- Do not close PRs.
|
||||
- End in MERGED state.
|
||||
- Clean up only after merge success.
|
||||
- Never push to main. Use `gh pr merge --squash` only.
|
||||
- Do not run `git push` at all in this command.
|
||||
4
.agents/skills/merge-pr/agents/openai.yaml
Normal file
4
.agents/skills/merge-pr/agents/openai.yaml
Normal file
@@ -0,0 +1,4 @@
|
||||
interface:
|
||||
display_name: "Merge PR"
|
||||
short_description: "Merge GitHub PRs via squash"
|
||||
default_prompt: "Use $merge-pr to merge a GitHub PR via squash after preparation."
|
||||
248
.agents/skills/prepare-pr/SKILL.md
Normal file
248
.agents/skills/prepare-pr/SKILL.md
Normal file
@@ -0,0 +1,248 @@
|
||||
---
|
||||
name: prepare-pr
|
||||
description: Prepare a GitHub PR for merge by rebasing onto main, fixing review findings, running gates, committing fixes, and pushing to the PR head branch. Use after /reviewpr. Never merge or push to main.
|
||||
---
|
||||
|
||||
# Prepare PR
|
||||
|
||||
## Overview
|
||||
|
||||
Prepare a PR branch for merge with review fixes, green gates, and an updated head branch.
|
||||
|
||||
## Inputs
|
||||
|
||||
- Ask for PR number or URL.
|
||||
- If missing, auto-detect from conversation.
|
||||
- If ambiguous, ask.
|
||||
|
||||
## Safety
|
||||
|
||||
- Never push to `main` or `origin/main`. Push only to the PR head branch.
|
||||
- Never run `git push` without specifying remote and branch explicitly. Do not run bare `git push`.
|
||||
- Do not run gateway stop commands. Do not kill processes. Do not touch port 18792.
|
||||
- Do not run `git clean -fdx`.
|
||||
- Do not run `git add -A` or `git add .`. Stage only specific files changed.
|
||||
|
||||
## Execution Rule
|
||||
|
||||
- Execute the workflow. Do not stop after printing the TODO checklist.
|
||||
- If delegating, require the delegate to run commands and capture outputs.
|
||||
|
||||
## Known Footguns
|
||||
|
||||
- If you see "fatal: not a git repository", you are in the wrong directory. Use `~/openclaw`.
|
||||
- Do not run `git clean -fdx`.
|
||||
- Do not run `git add -A` or `git add .`.
|
||||
|
||||
## Completion Criteria
|
||||
|
||||
- Rebase PR commits onto `origin/main`.
|
||||
- Fix all BLOCKER and IMPORTANT items from `.local/review.md`.
|
||||
- Run gates and pass.
|
||||
- Commit prep changes.
|
||||
- Push the updated HEAD back to the PR head branch.
|
||||
- Write `.local/prep.md` with a prep summary.
|
||||
- Output exactly: `PR is ready for /mergepr`.
|
||||
|
||||
## First: Create a TODO Checklist
|
||||
|
||||
Create a checklist of all prep steps, print it, then continue and execute the commands.
|
||||
|
||||
## Setup: Use a Worktree
|
||||
|
||||
Use an isolated worktree for all prep work.
|
||||
|
||||
```sh
|
||||
cd ~/openclaw
|
||||
# Sanity: confirm you are in the repo
|
||||
git rev-parse --show-toplevel
|
||||
|
||||
WORKTREE_DIR=".worktrees/pr-<PR>"
|
||||
```
|
||||
|
||||
Run all commands inside the worktree directory.
|
||||
|
||||
## Load Review Findings (Mandatory)
|
||||
|
||||
```sh
|
||||
if [ -f .local/review.md ]; then
|
||||
echo "Found review findings from /reviewpr"
|
||||
else
|
||||
echo "Missing .local/review.md. Run /reviewpr first and save findings."
|
||||
exit 1
|
||||
fi
|
||||
|
||||
# Read it
|
||||
sed -n '1,200p' .local/review.md
|
||||
```
|
||||
|
||||
## Steps
|
||||
|
||||
1. Identify PR meta (author, head branch, head repo URL)
|
||||
|
||||
```sh
|
||||
gh pr view <PR> --json number,title,author,headRefName,baseRefName,headRepository,body --jq '{number,title,author:.author.login,head:.headRefName,base:.baseRefName,headRepo:.headRepository.nameWithOwner,body}'
|
||||
contrib=$(gh pr view <PR> --json author --jq .author.login)
|
||||
head=$(gh pr view <PR> --json headRefName --jq .headRefName)
|
||||
head_repo_url=$(gh pr view <PR> --json headRepository --jq .headRepository.url)
|
||||
```
|
||||
|
||||
2. Fetch the PR branch tip into a local ref
|
||||
|
||||
```sh
|
||||
git fetch origin pull/<PR>/head:pr-<PR>
|
||||
```
|
||||
|
||||
3. Rebase PR commits onto latest main
|
||||
|
||||
```sh
|
||||
# Move worktree to the PR tip first
|
||||
git reset --hard pr-<PR>
|
||||
|
||||
# Rebase onto current main
|
||||
git fetch origin main
|
||||
git rebase origin/main
|
||||
```
|
||||
|
||||
If conflicts happen:
|
||||
|
||||
- Resolve each conflicted file.
|
||||
- Run `git add <resolved_file>` for each file.
|
||||
- Run `git rebase --continue`.
|
||||
|
||||
If the rebase gets confusing or you resolve conflicts 3 or more times, stop and report.
|
||||
|
||||
4. Fix issues from `.local/review.md`
|
||||
|
||||
- Fix all BLOCKER and IMPORTANT items.
|
||||
- NITs are optional.
|
||||
- Keep scope tight.
|
||||
|
||||
Keep a running log in `.local/prep.md`:
|
||||
|
||||
- List which review items you fixed.
|
||||
- List which files you touched.
|
||||
- Note behavior changes.
|
||||
|
||||
5. Update `CHANGELOG.md` if flagged in review
|
||||
|
||||
Check `.local/review.md` section H for guidance.
|
||||
If flagged and user-facing:
|
||||
|
||||
- Check if `CHANGELOG.md` exists.
|
||||
|
||||
```sh
|
||||
ls CHANGELOG.md 2>/dev/null
|
||||
```
|
||||
|
||||
- Follow existing format.
|
||||
- Add a concise entry with PR number and contributor.
|
||||
|
||||
6. Update docs if flagged in review
|
||||
|
||||
Check `.local/review.md` section G for guidance.
|
||||
If flagged, update only docs related to the PR changes.
|
||||
|
||||
7. Commit prep fixes
|
||||
|
||||
Stage only specific files:
|
||||
|
||||
```sh
|
||||
git add <file1> <file2> ...
|
||||
```
|
||||
|
||||
Preferred commit tool:
|
||||
|
||||
```sh
|
||||
committer "fix: <summary> (#<PR>) (thanks @$contrib)" <changed files>
|
||||
```
|
||||
|
||||
If `committer` is not found:
|
||||
|
||||
```sh
|
||||
git commit -m "fix: <summary> (#<PR>) (thanks @$contrib)"
|
||||
```
|
||||
|
||||
8. Run full gates before pushing
|
||||
|
||||
```sh
|
||||
pnpm install
|
||||
pnpm build
|
||||
pnpm ui:build
|
||||
pnpm check
|
||||
pnpm test
|
||||
```
|
||||
|
||||
Require all to pass. If something fails, fix, commit, and rerun. Allow at most 3 fix and rerun cycles. If gates still fail after 3 attempts, stop and report the failures. Do not loop indefinitely.
|
||||
|
||||
9. Push updates back to the PR head branch
|
||||
|
||||
```sh
|
||||
# Ensure remote for PR head exists
|
||||
git remote add prhead "$head_repo_url.git" 2>/dev/null || git remote set-url prhead "$head_repo_url.git"
|
||||
|
||||
# Use force with lease after rebase
|
||||
# Double check: $head must NOT be "main" or "master"
|
||||
echo "Pushing to branch: $head"
|
||||
if [ "$head" = "main" ] || [ "$head" = "master" ]; then
|
||||
echo "ERROR: head branch is main/master. This is wrong. Stopping."
|
||||
exit 1
|
||||
fi
|
||||
git push --force-with-lease prhead HEAD:$head
|
||||
```
|
||||
|
||||
10. Verify PR is not behind main (Mandatory)
|
||||
|
||||
```sh
|
||||
git fetch origin main
|
||||
git fetch origin pull/<PR>/head:pr-<PR>-verify --force
|
||||
git merge-base --is-ancestor origin/main pr-<PR>-verify && echo "PR is up to date with main" || echo "ERROR: PR is still behind main, rebase again"
|
||||
git branch -D pr-<PR>-verify 2>/dev/null || true
|
||||
```
|
||||
|
||||
If still behind main, repeat steps 2 through 9.
|
||||
|
||||
11. Write prep summary artifacts (Mandatory)
|
||||
|
||||
Update `.local/prep.md` with:
|
||||
|
||||
- Current HEAD sha from `git rev-parse HEAD`.
|
||||
- Short bullet list of changes.
|
||||
- Gate results.
|
||||
- Push confirmation.
|
||||
- Rebase verification result.
|
||||
|
||||
Create or overwrite `.local/prep.md` and verify it exists and is non-empty:
|
||||
|
||||
```sh
|
||||
git rev-parse HEAD
|
||||
ls -la .local/prep.md
|
||||
wc -l .local/prep.md
|
||||
```
|
||||
|
||||
12. Output
|
||||
|
||||
Include a diff stat summary:
|
||||
|
||||
```sh
|
||||
git diff --stat origin/main..HEAD
|
||||
git diff --shortstat origin/main..HEAD
|
||||
```
|
||||
|
||||
Report totals: X files changed, Y insertions(+), Z deletions(-).
|
||||
|
||||
If gates passed and push succeeded, print exactly:
|
||||
|
||||
```
|
||||
PR is ready for /mergepr
|
||||
```
|
||||
|
||||
Otherwise, list remaining failures and stop.
|
||||
|
||||
## Guardrails
|
||||
|
||||
- Worktree only.
|
||||
- Do not delete the worktree on success. `/mergepr` may reuse it.
|
||||
- Do not run `gh pr merge`.
|
||||
- Never push to main. Only push to the PR head branch.
|
||||
- Run and pass all gates before pushing.
|
||||
4
.agents/skills/prepare-pr/agents/openai.yaml
Normal file
4
.agents/skills/prepare-pr/agents/openai.yaml
Normal file
@@ -0,0 +1,4 @@
|
||||
interface:
|
||||
display_name: "Prepare PR"
|
||||
short_description: "Prepare GitHub PRs for merge"
|
||||
default_prompt: "Use $prepare-pr to prep a GitHub PR for merge without merging."
|
||||
228
.agents/skills/review-pr/SKILL.md
Normal file
228
.agents/skills/review-pr/SKILL.md
Normal file
@@ -0,0 +1,228 @@
|
||||
---
|
||||
name: review-pr
|
||||
description: Review-only GitHub pull request analysis with the gh CLI. Use when asked to review a PR, provide structured feedback, or assess readiness to land. Do not merge, push, or make code changes you intend to keep.
|
||||
---
|
||||
|
||||
# Review PR
|
||||
|
||||
## Overview
|
||||
|
||||
Perform a thorough review-only PR assessment and return a structured recommendation on readiness for /preparepr.
|
||||
|
||||
## Inputs
|
||||
|
||||
- Ask for PR number or URL.
|
||||
- If missing, always ask. Never auto-detect from conversation.
|
||||
- If ambiguous, ask.
|
||||
|
||||
## Safety
|
||||
|
||||
- Never push to `main` or `origin/main`, not during review, not ever.
|
||||
- Do not run `git push` at all during review. Treat review as read only.
|
||||
- Do not stop or kill the gateway. Do not run gateway stop commands. Do not kill processes on port 18792.
|
||||
|
||||
## Execution Rule
|
||||
|
||||
- Execute the workflow. Do not stop after printing the TODO checklist.
|
||||
- If delegating, require the delegate to run commands and capture outputs, not a plan.
|
||||
|
||||
## Known Failure Modes
|
||||
|
||||
- If you see "fatal: not a git repository", you are in the wrong directory. Use `~/openclaw`.
|
||||
- Do not stop after printing the checklist. That is not completion.
|
||||
|
||||
## Writing Style for Output
|
||||
|
||||
- Write casual and direct.
|
||||
- Avoid em dashes and en dashes. Use commas or separate sentences.
|
||||
|
||||
## Completion Criteria
|
||||
|
||||
- Run the commands in the worktree and inspect the PR directly.
|
||||
- Produce the structured review sections A through J.
|
||||
- Save the full review to `.local/review.md` inside the worktree.
|
||||
|
||||
## First: Create a TODO Checklist
|
||||
|
||||
Create a checklist of all review steps, print it, then continue and execute the commands.
|
||||
|
||||
## Setup: Use a Worktree
|
||||
|
||||
Use an isolated worktree for all review work.
|
||||
|
||||
```sh
|
||||
cd ~/Development/openclaw
|
||||
# Sanity: confirm you are in the repo
|
||||
git rev-parse --show-toplevel
|
||||
|
||||
WORKTREE_DIR=".worktrees/pr-<PR>"
|
||||
git fetch origin main
|
||||
|
||||
# Reuse existing worktree if it exists, otherwise create new
|
||||
if [ -d "$WORKTREE_DIR" ]; then
|
||||
cd "$WORKTREE_DIR"
|
||||
git checkout temp/pr-<PR> 2>/dev/null || git checkout -b temp/pr-<PR>
|
||||
git fetch origin main
|
||||
git reset --hard origin/main
|
||||
else
|
||||
git worktree add "$WORKTREE_DIR" -b temp/pr-<PR> origin/main
|
||||
cd "$WORKTREE_DIR"
|
||||
fi
|
||||
|
||||
# Create local scratch space that persists across /reviewpr to /preparepr to /mergepr
|
||||
mkdir -p .local
|
||||
```
|
||||
|
||||
Run all commands inside the worktree directory.
|
||||
Start on `origin/main` so you can check for existing implementations before looking at PR code.
|
||||
|
||||
## Steps
|
||||
|
||||
1. Identify PR meta and context
|
||||
|
||||
```sh
|
||||
gh pr view <PR> --json number,title,state,isDraft,author,baseRefName,headRefName,headRepository,url,body,labels,assignees,reviewRequests,files,additions,deletions --jq '{number,title,url,state,isDraft,author:.author.login,base:.baseRefName,head:.headRefName,headRepo:.headRepository.nameWithOwner,additions,deletions,files:.files|length,body}'
|
||||
```
|
||||
|
||||
2. Check if this already exists in main before looking at the PR branch
|
||||
|
||||
- Identify the core feature or fix from the PR title and description.
|
||||
- Search for existing implementations using keywords from the PR title, changed file paths, and function or component names from the diff.
|
||||
|
||||
```sh
|
||||
# Use keywords from the PR title and changed files
|
||||
rg -n "<keyword_from_pr_title>" -S src packages apps ui || true
|
||||
rg -n "<function_or_component_name>" -S src packages apps ui || true
|
||||
|
||||
git log --oneline --all --grep="<keyword_from_pr_title>" | head -20
|
||||
```
|
||||
|
||||
If it already exists, call it out as a BLOCKER or at least IMPORTANT.
|
||||
|
||||
3. Claim the PR
|
||||
|
||||
Assign yourself so others know someone is reviewing. Skip if the PR looks like spam or is a draft you plan to recommend closing.
|
||||
|
||||
```sh
|
||||
gh_user=$(gh api user --jq .login)
|
||||
gh pr edit <PR> --add-assignee "$gh_user"
|
||||
```
|
||||
|
||||
4. Read the PR description carefully
|
||||
|
||||
Use the body from step 1. Summarize goal, scope, and missing context.
|
||||
|
||||
5. Read the diff thoroughly
|
||||
|
||||
Minimum:
|
||||
|
||||
```sh
|
||||
gh pr diff <PR>
|
||||
```
|
||||
|
||||
If you need full code context locally, fetch the PR head to a local ref and diff it. Do not create a merge commit.
|
||||
|
||||
```sh
|
||||
git fetch origin pull/<PR>/head:pr-<PR>
|
||||
# Show changes without modifying the working tree
|
||||
|
||||
git diff --stat origin/main..pr-<PR>
|
||||
git diff origin/main..pr-<PR>
|
||||
```
|
||||
|
||||
If you want to browse the PR version of files directly, temporarily check out `pr-<PR>` in the worktree. Do not commit or push. Return to `temp/pr-<PR>` and reset to `origin/main` afterward.
|
||||
|
||||
```sh
|
||||
# Use only if needed
|
||||
# git checkout pr-<PR>
|
||||
# ...inspect files...
|
||||
|
||||
git checkout temp/pr-<PR>
|
||||
git reset --hard origin/main
|
||||
```
|
||||
|
||||
6. Validate the change is needed and valuable
|
||||
|
||||
Be honest. Call out low value AI slop.
|
||||
|
||||
7. Evaluate implementation quality
|
||||
|
||||
Review correctness, design, performance, and ergonomics.
|
||||
|
||||
8. Perform a security review
|
||||
|
||||
Assume OpenClaw subagents run with full disk access, including git, gh, and shell. Check auth, input validation, secrets, dependencies, tool safety, and privacy.
|
||||
|
||||
9. Review tests and verification
|
||||
|
||||
Identify what exists, what is missing, and what would be a minimal regression test.
|
||||
|
||||
10. Check docs
|
||||
|
||||
Check if the PR touches code with related documentation such as README, docs, inline API docs, or config examples.
|
||||
|
||||
- If docs exist for the changed area and the PR does not update them, flag as IMPORTANT.
|
||||
- If the PR adds a new feature or config option with no docs, flag as IMPORTANT.
|
||||
- If the change is purely internal with no user-facing impact, skip this.
|
||||
|
||||
11. Check changelog
|
||||
|
||||
Check if `CHANGELOG.md` exists and whether the PR warrants an entry.
|
||||
|
||||
- If the project has a changelog and the PR is user-facing, flag missing entry as IMPORTANT.
|
||||
- Leave the change for /preparepr, only flag it here.
|
||||
|
||||
12. Answer the key question
|
||||
|
||||
Decide if /preparepr can fix issues or the contributor must update the PR.
|
||||
|
||||
13. Save findings to the worktree
|
||||
|
||||
Write the full structured review sections A through J to `.local/review.md`.
|
||||
Create or overwrite the file and verify it exists and is non-empty.
|
||||
|
||||
```sh
|
||||
ls -la .local/review.md
|
||||
wc -l .local/review.md
|
||||
```
|
||||
|
||||
14. Output the structured review
|
||||
|
||||
Produce a review that matches what you saved to `.local/review.md`.
|
||||
|
||||
A) TL;DR recommendation
|
||||
|
||||
- One of: READY FOR /preparepr | NEEDS WORK | NEEDS DISCUSSION | NOT USEFUL (CLOSE)
|
||||
- 1 to 3 sentences.
|
||||
|
||||
B) What changed
|
||||
|
||||
C) What is good
|
||||
|
||||
D) Security findings
|
||||
|
||||
E) Concerns or questions (actionable)
|
||||
|
||||
- Numbered list.
|
||||
- Mark each item as BLOCKER, IMPORTANT, or NIT.
|
||||
- For each, point to file or area and propose a concrete fix.
|
||||
|
||||
F) Tests
|
||||
|
||||
G) Docs status
|
||||
|
||||
- State if related docs are up to date, missing, or not applicable.
|
||||
|
||||
H) Changelog
|
||||
|
||||
- State if `CHANGELOG.md` needs an entry and which category.
|
||||
|
||||
I) Follow ups (optional)
|
||||
|
||||
J) Suggested PR comment (optional)
|
||||
|
||||
## Guardrails
|
||||
|
||||
- Worktree only.
|
||||
- Do not delete the worktree after review.
|
||||
- Review only, do not merge, do not push.
|
||||
4
.agents/skills/review-pr/agents/openai.yaml
Normal file
4
.agents/skills/review-pr/agents/openai.yaml
Normal file
@@ -0,0 +1,4 @@
|
||||
interface:
|
||||
display_name: "Review PR"
|
||||
short_description: "Review GitHub PRs without merging"
|
||||
default_prompt: "Use $review-pr to perform a thorough, review-only GitHub PR review."
|
||||
4
.github/ISSUE_TEMPLATE/config.yml
vendored
4
.github/ISSUE_TEMPLATE/config.yml
vendored
@@ -2,7 +2,7 @@ blank_issues_enabled: true
|
||||
contact_links:
|
||||
- name: Onboarding
|
||||
url: https://discord.gg/clawd
|
||||
about: New to Clawdbot? Join Discord for setup guidance from Krill in #help.
|
||||
about: New to Clawdbot? Join Discord for setup guidance from Krill in \#help.
|
||||
- name: Support
|
||||
url: https://discord.gg/clawd
|
||||
about: Get help from Krill and the community on Discord in #help.
|
||||
about: Get help from Krill and the community on Discord in \#help.
|
||||
|
||||
6
.gitignore
vendored
6
.gitignore
vendored
@@ -64,10 +64,14 @@ apps/ios/*.mobileprovision
|
||||
|
||||
# Local untracked files
|
||||
.local/
|
||||
.vscode/
|
||||
IDENTITY.md
|
||||
USER.md
|
||||
.tgz
|
||||
|
||||
# local tooling
|
||||
.serena/
|
||||
|
||||
# Agent credentials and memory (NEVER COMMIT)
|
||||
memory/
|
||||
.agent/*.json
|
||||
!.agent/workflows/
|
||||
|
||||
@@ -8,98 +8,63 @@ Input
|
||||
- If missing: use the most recent PR mentioned in the conversation.
|
||||
- If ambiguous: ask.
|
||||
|
||||
Do (review-only)
|
||||
Goal: produce a thorough review and a clear recommendation (READY for /landpr vs NEEDS WORK). Do NOT merge, do NOT push, do NOT make changes in the repo as part of this command.
|
||||
Do (end-to-end)
|
||||
Goal: PR must end in GitHub state = MERGED (never CLOSED). Use `gh pr merge` with `--rebase` or `--squash`.
|
||||
|
||||
1. Identify PR meta + context
|
||||
1. Repo clean: `git status`.
|
||||
2. Identify PR meta (author + head branch):
|
||||
|
||||
```sh
|
||||
gh pr view <PR> --json number,title,state,isDraft,author,baseRefName,headRefName,headRepository,url,body,labels,assignees,reviewRequests,files,additions,deletions --jq '{number,title,url,state,isDraft,author:.author.login,base:.baseRefName,head:.headRefName,headRepo:.headRepository.nameWithOwner,additions,deletions,files:.files|length}'
|
||||
gh pr view <PR> --json number,title,author,headRefName,baseRefName,headRepository --jq '{number,title,author:.author.login,head:.headRefName,base:.baseRefName,headRepo:.headRepository.nameWithOwner}'
|
||||
contrib=$(gh pr view <PR> --json author --jq .author.login)
|
||||
head=$(gh pr view <PR> --json headRefName --jq .headRefName)
|
||||
head_repo_url=$(gh pr view <PR> --json headRepository --jq .headRepository.url)
|
||||
```
|
||||
|
||||
2. Read the PR description carefully
|
||||
- Summarize the stated goal, scope, and any “why now?” rationale.
|
||||
- Call out any missing context: motivation, alternatives considered, rollout/compat notes, risk.
|
||||
3. Fast-forward base:
|
||||
- `git checkout main`
|
||||
- `git pull --ff-only`
|
||||
4. Create temp base branch from main:
|
||||
- `git checkout -b temp/landpr-<ts-or-pr>`
|
||||
5. Check out PR branch locally:
|
||||
- `gh pr checkout <PR>`
|
||||
6. Rebase PR branch onto temp base:
|
||||
- `git rebase temp/landpr-<ts-or-pr>`
|
||||
- Fix conflicts; keep history tidy.
|
||||
7. Fix + tests + changelog:
|
||||
- Implement fixes + add/adjust tests
|
||||
- Update `CHANGELOG.md` and mention `#<PR>` + `@$contrib`
|
||||
8. Decide merge strategy:
|
||||
- Rebase if we want to preserve commit history
|
||||
- Squash if we want a single clean commit
|
||||
- If unclear, ask
|
||||
9. Full gate (BEFORE commit):
|
||||
- `pnpm lint && pnpm build && pnpm test`
|
||||
10. Commit via committer (include # + contributor in commit message):
|
||||
- `committer "fix: <summary> (#<PR>) (thanks @$contrib)" CHANGELOG.md <changed files>`
|
||||
- `land_sha=$(git rev-parse HEAD)`
|
||||
11. Push updated PR branch (rebase => usually needs force):
|
||||
|
||||
3. Read the diff thoroughly (prefer full diff)
|
||||
```sh
|
||||
git remote add prhead "$head_repo_url.git" 2>/dev/null || git remote set-url prhead "$head_repo_url.git"
|
||||
git push --force-with-lease prhead HEAD:$head
|
||||
```
|
||||
|
||||
```sh
|
||||
gh pr diff <PR>
|
||||
# If you need more surrounding context for files:
|
||||
gh pr checkout <PR> # optional; still review-only
|
||||
git show --stat
|
||||
```
|
||||
12. Merge PR (must show MERGED on GitHub):
|
||||
- Rebase: `gh pr merge <PR> --rebase`
|
||||
- Squash: `gh pr merge <PR> --squash`
|
||||
- Never `gh pr close` (closing is wrong)
|
||||
13. Sync main:
|
||||
- `git checkout main`
|
||||
- `git pull --ff-only`
|
||||
14. Comment on PR with what we did + SHAs + thanks:
|
||||
|
||||
4. Validate the change is needed / valuable
|
||||
- What user/customer/dev pain does this solve?
|
||||
- Is this change the smallest reasonable fix?
|
||||
- Are we introducing complexity for marginal benefit?
|
||||
- Are we changing behavior/contract in a way that needs docs or a release note?
|
||||
```sh
|
||||
merge_sha=$(gh pr view <PR> --json mergeCommit --jq '.mergeCommit.oid')
|
||||
gh pr comment <PR> --body "Landed via temp rebase onto main.\n\n- Gate: pnpm lint && pnpm build && pnpm test\n- Land commit: $land_sha\n- Merge commit: $merge_sha\n\nThanks @$contrib!"
|
||||
```
|
||||
|
||||
5. Evaluate implementation quality + optimality
|
||||
- Correctness: edge cases, error handling, null/undefined, concurrency, ordering.
|
||||
- Design: is the abstraction/architecture appropriate or over/under-engineered?
|
||||
- Performance: hot paths, allocations, queries, network, N+1s, caching.
|
||||
- Security/privacy: authz/authn, input validation, secrets, logging PII.
|
||||
- Backwards compatibility: public APIs, config, migrations.
|
||||
- Style consistency: formatting, naming, patterns used elsewhere.
|
||||
|
||||
6. Tests & verification
|
||||
- Identify what’s covered by tests (unit/integration/e2e).
|
||||
- Are there regression tests for the bug fixed / scenario added?
|
||||
- Missing tests? Call out exact cases that should be added.
|
||||
- If tests are present, do they actually assert the important behavior (not just snapshots / happy path)?
|
||||
|
||||
7. Follow-up refactors / cleanup suggestions
|
||||
- Any code that should be simplified before merge?
|
||||
- Any TODOs that should be tickets vs addressed now?
|
||||
- Any deprecations, docs, types, or lint rules we should adjust?
|
||||
|
||||
8. Key questions to answer explicitly
|
||||
- Can we fix everything ourselves in a follow-up, or does the contributor need to update this PR?
|
||||
- Any blocking concerns (must-fix before merge)?
|
||||
- Is this PR ready to land, or does it need work?
|
||||
|
||||
9. Output (structured)
|
||||
Produce a review with these sections:
|
||||
|
||||
A) TL;DR recommendation
|
||||
|
||||
- One of: READY FOR /landpr | NEEDS WORK | NEEDS DISCUSSION
|
||||
- 1–3 sentence rationale.
|
||||
|
||||
B) What changed
|
||||
|
||||
- Brief bullet summary of the diff/behavioral changes.
|
||||
|
||||
C) What’s good
|
||||
|
||||
- Bullets: correctness, simplicity, tests, docs, ergonomics, etc.
|
||||
|
||||
D) Concerns / questions (actionable)
|
||||
|
||||
- Numbered list.
|
||||
- Mark each item as:
|
||||
- BLOCKER (must fix before merge)
|
||||
- IMPORTANT (should fix before merge)
|
||||
- NIT (optional)
|
||||
- For each: point to the file/area and propose a concrete fix or alternative.
|
||||
|
||||
E) Tests
|
||||
|
||||
- What exists.
|
||||
- What’s missing (specific scenarios).
|
||||
|
||||
F) Follow-ups (optional)
|
||||
|
||||
- Non-blocking refactors/tickets to open later.
|
||||
|
||||
G) Suggested PR comment (optional)
|
||||
|
||||
- Offer: “Want me to draft a PR comment to the author?”
|
||||
- If yes, provide a ready-to-paste comment summarizing the above, with clear asks.
|
||||
|
||||
Rules / Guardrails
|
||||
|
||||
- Review only: do not merge (`gh pr merge`), do not push branches, do not edit code.
|
||||
- If you need clarification, ask questions rather than guessing.
|
||||
15. Verify PR state == MERGED:
|
||||
- `gh pr view <PR> --json state --jq .state`
|
||||
16. Delete temp branch:
|
||||
- `git branch -D temp/landpr-<ts-or-pr>`
|
||||
|
||||
3
.vscode/extensions.json
vendored
Normal file
3
.vscode/extensions.json
vendored
Normal file
@@ -0,0 +1,3 @@
|
||||
{
|
||||
"recommendations": ["oxc.oxc-vscode"]
|
||||
}
|
||||
22
.vscode/settings.json
vendored
Normal file
22
.vscode/settings.json
vendored
Normal file
@@ -0,0 +1,22 @@
|
||||
{
|
||||
"editor.formatOnSave": true,
|
||||
"files.insertFinalNewline": true,
|
||||
"files.trimFinalNewlines": true,
|
||||
"[javascript]": {
|
||||
"editor.defaultFormatter": "oxc.oxc-vscode"
|
||||
},
|
||||
"[typescriptreact]": {
|
||||
"editor.defaultFormatter": "oxc.oxc-vscode"
|
||||
},
|
||||
"[typescript]": {
|
||||
"editor.defaultFormatter": "oxc.oxc-vscode"
|
||||
},
|
||||
"[json]": {
|
||||
"editor.defaultFormatter": "oxc.oxc-vscode"
|
||||
},
|
||||
"typescript.preferences.importModuleSpecifierEnding": "js",
|
||||
"typescript.reportStyleChecksAsWarnings": false,
|
||||
"typescript.updateImportsOnFileMove.enabled": "always",
|
||||
"typescript.tsdk": "node_modules/typescript/lib",
|
||||
"typescript.experimental.useTsgo": true
|
||||
}
|
||||
@@ -58,6 +58,7 @@
|
||||
- Node remains supported for running built output (`dist/*`) and production installs.
|
||||
- Mac packaging (dev): `scripts/package-mac-app.sh` defaults to current arch. Release checklist: `docs/platforms/mac/release.md`.
|
||||
- Type-check/build: `pnpm build`
|
||||
- TypeScript checks: `pnpm tsgo`
|
||||
- Lint/format: `pnpm check`
|
||||
- Tests: `pnpm test` (vitest); coverage: `pnpm test:coverage`
|
||||
|
||||
|
||||
43
CHANGELOG.md
43
CHANGELOG.md
@@ -2,12 +2,28 @@
|
||||
|
||||
Docs: https://docs.openclaw.ai
|
||||
|
||||
## 2026.2.3
|
||||
## 2026.2.4
|
||||
|
||||
### Changes
|
||||
|
||||
- Agents: bump pi-mono packages to 0.52.5. (#9949) Thanks @gumadeiras.
|
||||
- Models: default Anthropic model to `anthropic/claude-opus-4-6`. (#9853) Thanks @TinyTb.
|
||||
- Models/Onboarding: refresh provider defaults, update OpenAI/OpenAI Codex wizard defaults, and harden model allowlist initialization for first-time configs with matching docs/tests. (#9911) Thanks @gumadeiras.
|
||||
- Telegram: auto-inject forum topic `threadId` in message tool and subagent announce so media, buttons, and subagent results land in the correct topic instead of General. (#7235) Thanks @Lukavyi.
|
||||
- Security: add skill/plugin code safety scanner that detects dangerous patterns (command injection, eval, data exfiltration, obfuscated code, crypto mining, env harvesting) in installed extensions. Integrated into `openclaw security audit --deep` and plugin install flow; scan failures surface as warnings. (#9806) Thanks @abdelsfane.
|
||||
- CLI: sort `openclaw --help` commands (and options) alphabetically. (#8068) Thanks @deepsoumya617.
|
||||
- Telegram: remove last `@ts-nocheck` from `bot-handlers.ts`, use Grammy types directly, deduplicate `StickerMetadata`. Zero `@ts-nocheck` remaining in `src/telegram/`. (#9206)
|
||||
- Telegram: remove `@ts-nocheck` from `bot-message.ts`, type deps via `Omit<BuildTelegramMessageContextParams>`, widen `allMedia` to `TelegramMediaRef[]`. (#9180)
|
||||
- Telegram: remove `@ts-nocheck` from `bot.ts`, fix duplicate `bot.catch` error handler (Grammy overrides), remove dead reaction `message_thread_id` routing, harden sticker cache guard. (#9077)
|
||||
- Telegram: allow per-group and per-topic `groupPolicy` overrides under `channels.telegram.groups`. (#9775) Thanks @nicolasstanley.
|
||||
- Feishu: expand channel handling (posts with images, doc links, routing, reactions/typing, replies, native commands). (#8975) Thanks @jiulingyun.
|
||||
- Onboarding: add Cloudflare AI Gateway provider setup and docs. (#7914) Thanks @roerohan.
|
||||
- Onboarding: add Moonshot (.cn) auth choice and keep the China base URL when preserving defaults. (#7180) Thanks @waynelwz.
|
||||
- Onboarding: add xAI (Grok) auth choice and provider defaults. (#9885) Thanks @grp06.
|
||||
- Docs: clarify tmux send-keys for TUI by splitting text and Enter. (#7737) Thanks @Wangnov.
|
||||
- Docs: mirror the landing page revamp for zh-CN (features, quickstart, docs directory, network model, credits). (#8994) Thanks @joshp123.
|
||||
- Docs: strengthen secure DM mode guidance for multi-user inboxes with an explicit warning and example. (#9377) Thanks @Shrinija17.
|
||||
- Messages: add per-channel and per-account responsePrefix overrides across channels. (#9001) Thanks @mudrii.
|
||||
- Cron: add announce delivery mode for isolated jobs (CLI + Control UI) and delivery mode config.
|
||||
- Cron: default isolated jobs to announce delivery; accept ISO 8601 `schedule.at` in tool inputs.
|
||||
- Cron: hard-migrate isolated jobs to announce/none delivery; drop legacy post-to-main/payload delivery fields and `atMs` inputs.
|
||||
@@ -17,15 +33,40 @@ Docs: https://docs.openclaw.ai
|
||||
|
||||
### Fixes
|
||||
|
||||
- Models: add forward-compat fallback for `openai-codex/gpt-5.3-codex` when model registry hasn't discovered it yet. (#9989) Thanks @w1kke.
|
||||
- Auto-reply/Docs: normalize `extra-high` (and spaced variants) to `xhigh` for Codex thinking levels, and align Codex 5.3 FAQ examples. (#9976) Thanks @slonce70.
|
||||
- Compaction: remove orphaned `tool_result` messages during history pruning to prevent session corruption from aborted tool calls. (#9868, fixes #9769, #9724, #9672)
|
||||
- Telegram: pass `parentPeer` for forum topic binding inheritance so group-level bindings apply to all topics within the group. (#9789, fixes #9545, #9351)
|
||||
- CLI: pass `--disable-warning=ExperimentalWarning` as a Node CLI option when respawning (avoid disallowed `NODE_OPTIONS` usage; fixes npm pack). (#9691) Thanks @18-RAJAT.
|
||||
- CLI: resolve bundled Chrome extension assets by walking up to the nearest assets directory; add resolver and clipboard tests. (#8914) Thanks @kelvinCB.
|
||||
- Tests: stabilize Windows ACL coverage with deterministic os.userInfo mocking. (#9335) Thanks @M00N7682.
|
||||
- Exec approvals: coerce bare string allowlist entries to objects to prevent allowlist corruption. (#9903, fixes #9790) Thanks @mcaxtr.
|
||||
- Heartbeat: allow explicit accountId routing for multi-account channels. (#8702) Thanks @lsh411.
|
||||
- TUI/Gateway: handle non-streaming finals, refresh history for non-local chat runs, and avoid event gap warnings for targeted tool streams. (#8432) Thanks @gumadeiras.
|
||||
- Shell completion: auto-detect and migrate slow dynamic patterns to cached files for faster terminal startup; add completion health checks to doctor/update/onboard.
|
||||
- Telegram: honor session model overrides in inline model selection. (#8193) Thanks @gildo.
|
||||
- Web UI: fix agent model selection saves for default/non-default agents and wrap long workspace paths. Thanks @Takhoffman.
|
||||
- Web UI: resolve header logo path when `gateway.controlUi.basePath` is set. (#7178) Thanks @Yeom-JinHo.
|
||||
- Web UI: apply button styling to the new-messages indicator.
|
||||
- Onboarding: infer auth choice from non-interactive API key flags. (#8484) Thanks @f-trycua.
|
||||
- Security: keep untrusted channel metadata out of system prompts (Slack/Discord). Thanks @KonstantinMirin.
|
||||
- Security: redact channel credentials (tokens, passwords, API keys, secrets) from gateway config APIs and preserve secrets during Control UI round-trips. (#9858) Thanks @abdelsfane.
|
||||
- Discord: treat allowlisted senders as owner for system-prompt identity hints while keeping channel topics untrusted.
|
||||
- Slack: strip `<@...>` mention tokens before command matching so `/new` and `/reset` work when prefixed with a mention. (#9971) Thanks @ironbyte-rgb.
|
||||
- Security: enforce sandboxed media paths for message tool attachments. (#9182) Thanks @victormier.
|
||||
- Security: require explicit credentials for gateway URL overrides to prevent credential leakage. (#8113) Thanks @victormier.
|
||||
- Security: gate `whatsapp_login` tool to owner senders and default-deny non-owner contexts. (#8768) Thanks @victormier.
|
||||
- Voice call: harden webhook verification with host allowlists/proxy trust and keep ngrok loopback bypass.
|
||||
- Voice call: add regression coverage for anonymous inbound caller IDs with allowlist policy. (#8104) Thanks @victormier.
|
||||
- Cron: accept epoch timestamps and 0ms durations in CLI `--at` parsing.
|
||||
- Cron: reload store data when the store file is recreated or mtime changes.
|
||||
- Cron: prevent `recomputeNextRuns` from skipping due jobs when timer fires late by reordering `onTimer` flow. (#9823, fixes #9788) Thanks @pycckuu.
|
||||
- Cron: deliver announce runs directly, honor delivery mode, and respect wakeMode for summaries. (#8540) Thanks @tyler6204.
|
||||
- Cron: correct announce delivery inference for thread session keys and null delivery inputs. (#9733) Thanks @tyler6204.
|
||||
- Telegram: include forward_from_chat metadata in forwarded messages and harden cron delivery target checks. (#8392) Thanks @Glucksberg.
|
||||
- Telegram: preserve DM topic threadId in deliveryContext. (#9039) Thanks @lailoo.
|
||||
- macOS: fix cron payload summary rendering and ISO 8601 formatter concurrency safety.
|
||||
- Security: require gateway auth for Canvas host and A2UI assets. (#9518) Thanks @coygeek.
|
||||
|
||||
## 2026.2.2-3
|
||||
|
||||
|
||||
@@ -22,6 +22,9 @@ Welcome to the lobster tank! 🦞
|
||||
- **Christoph Nakazawa** - JS Infra
|
||||
- GitHub: [@cpojer](https://github.com/cpojer) · X: [@cnakazawa](https://x.com/cnakazawa)
|
||||
|
||||
- **Gustavo Madeira Santana** - Multi-agents, CLI, web UI
|
||||
- GitHub: [@gumadeiras](https://github.com/gumadeiras) · X: [@gumadeiras](https://x.com/gumadeiras)
|
||||
|
||||
## How to Contribute
|
||||
|
||||
1. **Bugs & small fixes** → Open a PR!
|
||||
|
||||
82
README.md
82
README.md
@@ -34,7 +34,7 @@ New install? Start here: [Getting started](https://docs.openclaw.ai/start/gettin
|
||||
- **[Anthropic](https://www.anthropic.com/)** (Claude Pro/Max)
|
||||
- **[OpenAI](https://openai.com/)** (ChatGPT/Codex)
|
||||
|
||||
Model note: while any model is supported, I strongly recommend **Anthropic Pro/Max (100/200) + Opus 4.5** for long‑context strength and better prompt‑injection resistance. See [Onboarding](https://docs.openclaw.ai/start/onboarding).
|
||||
Model note: while any model is supported, I strongly recommend **Anthropic Pro/Max (100/200) + Opus 4.6** for long‑context strength and better prompt‑injection resistance. See [Onboarding](https://docs.openclaw.ai/start/onboarding).
|
||||
|
||||
## Models (selection + auth)
|
||||
|
||||
@@ -316,7 +316,7 @@ Minimal `~/.openclaw/openclaw.json` (model + defaults):
|
||||
```json5
|
||||
{
|
||||
agent: {
|
||||
model: "anthropic/claude-opus-4-5",
|
||||
model: "anthropic/claude-opus-4-6",
|
||||
},
|
||||
}
|
||||
```
|
||||
@@ -496,44 +496,46 @@ Special thanks to Adam Doppelt for lobster.bot.
|
||||
Thanks to all clawtributors:
|
||||
|
||||
<p align="left">
|
||||
<a href="https://github.com/steipete"><img src="https://avatars.githubusercontent.com/u/58493?v=4&s=48" width="48" height="48" alt="steipete" title="steipete"/></a> <a href="https://github.com/cpojer"><img src="https://avatars.githubusercontent.com/u/13352?v=4&s=48" width="48" height="48" alt="cpojer" title="cpojer"/></a> <a href="https://github.com/plum-dawg"><img src="https://avatars.githubusercontent.com/u/5909950?v=4&s=48" width="48" height="48" alt="plum-dawg" title="plum-dawg"/></a> <a href="https://github.com/bohdanpodvirnyi"><img src="https://avatars.githubusercontent.com/u/31819391?v=4&s=48" width="48" height="48" alt="bohdanpodvirnyi" title="bohdanpodvirnyi"/></a> <a href="https://github.com/iHildy"><img src="https://avatars.githubusercontent.com/u/25069719?v=4&s=48" width="48" height="48" alt="iHildy" title="iHildy"/></a> <a href="https://github.com/jaydenfyi"><img src="https://avatars.githubusercontent.com/u/213395523?v=4&s=48" width="48" height="48" alt="jaydenfyi" title="jaydenfyi"/></a> <a href="https://github.com/joshp123"><img src="https://avatars.githubusercontent.com/u/1497361?v=4&s=48" width="48" height="48" alt="joshp123" title="joshp123"/></a> <a href="https://github.com/joaohlisboa"><img src="https://avatars.githubusercontent.com/u/8200873?v=4&s=48" width="48" height="48" alt="joaohlisboa" title="joaohlisboa"/></a> <a href="https://github.com/mneves75"><img src="https://avatars.githubusercontent.com/u/2423436?v=4&s=48" width="48" height="48" alt="mneves75" title="mneves75"/></a> <a href="https://github.com/MatthieuBizien"><img src="https://avatars.githubusercontent.com/u/173090?v=4&s=48" width="48" height="48" alt="MatthieuBizien" title="MatthieuBizien"/></a>
|
||||
<a href="https://github.com/MaudeBot"><img src="https://avatars.githubusercontent.com/u/255777700?v=4&s=48" width="48" height="48" alt="MaudeBot" title="MaudeBot"/></a> <a href="https://github.com/Glucksberg"><img src="https://avatars.githubusercontent.com/u/80581902?v=4&s=48" width="48" height="48" alt="Glucksberg" title="Glucksberg"/></a> <a href="https://github.com/rahthakor"><img src="https://avatars.githubusercontent.com/u/8470553?v=4&s=48" width="48" height="48" alt="rahthakor" title="rahthakor"/></a> <a href="https://github.com/vrknetha"><img src="https://avatars.githubusercontent.com/u/20596261?v=4&s=48" width="48" height="48" alt="vrknetha" title="vrknetha"/></a> <a href="https://github.com/radek-paclt"><img src="https://avatars.githubusercontent.com/u/50451445?v=4&s=48" width="48" height="48" alt="radek-paclt" title="radek-paclt"/></a> <a href="https://github.com/vignesh07"><img src="https://avatars.githubusercontent.com/u/1436853?v=4&s=48" width="48" height="48" alt="vignesh07" title="vignesh07"/></a> <a href="https://github.com/tobiasbischoff"><img src="https://avatars.githubusercontent.com/u/711564?v=4&s=48" width="48" height="48" alt="Tobias Bischoff" title="Tobias Bischoff"/></a> <a href="https://github.com/sebslight"><img src="https://avatars.githubusercontent.com/u/19554889?v=4&s=48" width="48" height="48" alt="sebslight" title="sebslight"/></a> <a href="https://github.com/czekaj"><img src="https://avatars.githubusercontent.com/u/1464539?v=4&s=48" width="48" height="48" alt="czekaj" title="czekaj"/></a> <a href="https://github.com/mukhtharcm"><img src="https://avatars.githubusercontent.com/u/56378562?v=4&s=48" width="48" height="48" alt="mukhtharcm" title="mukhtharcm"/></a>
|
||||
<a href="https://github.com/maxsumrall"><img src="https://avatars.githubusercontent.com/u/628843?v=4&s=48" width="48" height="48" alt="maxsumrall" title="maxsumrall"/></a> <a href="https://github.com/xadenryan"><img src="https://avatars.githubusercontent.com/u/165437834?v=4&s=48" width="48" height="48" alt="xadenryan" title="xadenryan"/></a> <a href="https://github.com/VACInc"><img src="https://avatars.githubusercontent.com/u/3279061?v=4&s=48" width="48" height="48" alt="VACInc" title="VACInc"/></a> <a href="https://github.com/mbelinky"><img src="https://avatars.githubusercontent.com/u/132747814?v=4&s=48" width="48" height="48" alt="Mariano Belinky" title="Mariano Belinky"/></a> <a href="https://github.com/rodrigouroz"><img src="https://avatars.githubusercontent.com/u/384037?v=4&s=48" width="48" height="48" alt="rodrigouroz" title="rodrigouroz"/></a> <a href="https://github.com/tyler6204"><img src="https://avatars.githubusercontent.com/u/64381258?v=4&s=48" width="48" height="48" alt="tyler6204" title="tyler6204"/></a> <a href="https://github.com/juanpablodlc"><img src="https://avatars.githubusercontent.com/u/92012363?v=4&s=48" width="48" height="48" alt="juanpablodlc" title="juanpablodlc"/></a> <a href="https://github.com/conroywhitney"><img src="https://avatars.githubusercontent.com/u/249891?v=4&s=48" width="48" height="48" alt="conroywhitney" title="conroywhitney"/></a> <a href="https://github.com/hsrvc"><img src="https://avatars.githubusercontent.com/u/129702169?v=4&s=48" width="48" height="48" alt="hsrvc" title="hsrvc"/></a> <a href="https://github.com/magimetal"><img src="https://avatars.githubusercontent.com/u/36491250?v=4&s=48" width="48" height="48" alt="magimetal" title="magimetal"/></a>
|
||||
<a href="https://github.com/zerone0x"><img src="https://avatars.githubusercontent.com/u/39543393?v=4&s=48" width="48" height="48" alt="zerone0x" title="zerone0x"/></a> <a href="https://github.com/meaningfool"><img src="https://avatars.githubusercontent.com/u/2862331?v=4&s=48" width="48" height="48" alt="meaningfool" title="meaningfool"/></a> <a href="https://github.com/patelhiren"><img src="https://avatars.githubusercontent.com/u/172098?v=4&s=48" width="48" height="48" alt="patelhiren" title="patelhiren"/></a> <a href="https://github.com/NicholasSpisak"><img src="https://avatars.githubusercontent.com/u/129075147?v=4&s=48" width="48" height="48" alt="NicholasSpisak" title="NicholasSpisak"/></a> <a href="https://github.com/jonisjongithub"><img src="https://avatars.githubusercontent.com/u/86072337?v=4&s=48" width="48" height="48" alt="jonisjongithub" title="jonisjongithub"/></a> <a href="https://github.com/AbhisekBasu1"><img src="https://avatars.githubusercontent.com/u/40645221?v=4&s=48" width="48" height="48" alt="abhisekbasu1" title="abhisekbasu1"/></a> <a href="https://github.com/jamesgroat"><img src="https://avatars.githubusercontent.com/u/2634024?v=4&s=48" width="48" height="48" alt="jamesgroat" title="jamesgroat"/></a> <a href="https://github.com/claude"><img src="https://avatars.githubusercontent.com/u/81847?v=4&s=48" width="48" height="48" alt="claude" title="claude"/></a> <a href="https://github.com/JustYannicc"><img src="https://avatars.githubusercontent.com/u/52761674?v=4&s=48" width="48" height="48" alt="JustYannicc" title="JustYannicc"/></a> <a href="https://github.com/Hyaxia"><img src="https://avatars.githubusercontent.com/u/36747317?v=4&s=48" width="48" height="48" alt="Hyaxia" title="Hyaxia"/></a>
|
||||
<a href="https://github.com/dantelex"><img src="https://avatars.githubusercontent.com/u/631543?v=4&s=48" width="48" height="48" alt="dantelex" title="dantelex"/></a> <a href="https://github.com/SocialNerd42069"><img src="https://avatars.githubusercontent.com/u/118244303?v=4&s=48" width="48" height="48" alt="SocialNerd42069" title="SocialNerd42069"/></a> <a href="https://github.com/daveonkels"><img src="https://avatars.githubusercontent.com/u/533642?v=4&s=48" width="48" height="48" alt="daveonkels" title="daveonkels"/></a> <a href="https://github.com/apps/google-labs-jules"><img src="https://avatars.githubusercontent.com/in/842251?v=4&s=48" width="48" height="48" alt="google-labs-jules[bot]" title="google-labs-jules[bot]"/></a> <a href="https://github.com/lc0rp"><img src="https://avatars.githubusercontent.com/u/2609441?v=4&s=48" width="48" height="48" alt="lc0rp" title="lc0rp"/></a> <a href="https://github.com/mousberg"><img src="https://avatars.githubusercontent.com/u/57605064?v=4&s=48" width="48" height="48" alt="mousberg" title="mousberg"/></a> <a href="https://github.com/adam91holt"><img src="https://avatars.githubusercontent.com/u/9592417?v=4&s=48" width="48" height="48" alt="adam91holt" title="adam91holt"/></a> <a href="https://github.com/hougangdev"><img src="https://avatars.githubusercontent.com/u/105773686?v=4&s=48" width="48" height="48" alt="hougangdev" title="hougangdev"/></a> <a href="https://github.com/gumadeiras"><img src="https://avatars.githubusercontent.com/u/5599352?v=4&s=48" width="48" height="48" alt="gumadeiras" title="gumadeiras"/></a> <a href="https://github.com/shakkernerd"><img src="https://avatars.githubusercontent.com/u/165377636?v=4&s=48" width="48" height="48" alt="shakkernerd" title="shakkernerd"/></a>
|
||||
<a href="https://github.com/mteam88"><img src="https://avatars.githubusercontent.com/u/84196639?v=4&s=48" width="48" height="48" alt="mteam88" title="mteam88"/></a> <a href="https://github.com/hirefrank"><img src="https://avatars.githubusercontent.com/u/183158?v=4&s=48" width="48" height="48" alt="hirefrank" title="hirefrank"/></a> <a href="https://github.com/joeynyc"><img src="https://avatars.githubusercontent.com/u/17919866?v=4&s=48" width="48" height="48" alt="joeynyc" title="joeynyc"/></a> <a href="https://github.com/orlyjamie"><img src="https://avatars.githubusercontent.com/u/6668807?v=4&s=48" width="48" height="48" alt="orlyjamie" title="orlyjamie"/></a> <a href="https://github.com/dbhurley"><img src="https://avatars.githubusercontent.com/u/5251425?v=4&s=48" width="48" height="48" alt="dbhurley" title="dbhurley"/></a> <a href="https://github.com/omniwired"><img src="https://avatars.githubusercontent.com/u/322761?v=4&s=48" width="48" height="48" alt="Eng. Juan Combetto" title="Eng. Juan Combetto"/></a> <a href="https://github.com/TSavo"><img src="https://avatars.githubusercontent.com/u/877990?v=4&s=48" width="48" height="48" alt="TSavo" title="TSavo"/></a> <a href="https://github.com/aerolalit"><img src="https://avatars.githubusercontent.com/u/17166039?v=4&s=48" width="48" height="48" alt="aerolalit" title="aerolalit"/></a> <a href="https://github.com/julianengel"><img src="https://avatars.githubusercontent.com/u/10634231?v=4&s=48" width="48" height="48" alt="julianengel" title="julianengel"/></a> <a href="https://github.com/bradleypriest"><img src="https://avatars.githubusercontent.com/u/167215?v=4&s=48" width="48" height="48" alt="bradleypriest" title="bradleypriest"/></a>
|
||||
<a href="https://github.com/benithors"><img src="https://avatars.githubusercontent.com/u/20652882?v=4&s=48" width="48" height="48" alt="benithors" title="benithors"/></a> <a href="https://github.com/rohannagpal"><img src="https://avatars.githubusercontent.com/u/4009239?v=4&s=48" width="48" height="48" alt="rohannagpal" title="rohannagpal"/></a> <a href="https://github.com/timolins"><img src="https://avatars.githubusercontent.com/u/1440854?v=4&s=48" width="48" height="48" alt="timolins" title="timolins"/></a> <a href="https://github.com/f-trycua"><img src="https://avatars.githubusercontent.com/u/195596869?v=4&s=48" width="48" height="48" alt="f-trycua" title="f-trycua"/></a> <a href="https://github.com/benostein"><img src="https://avatars.githubusercontent.com/u/31802821?v=4&s=48" width="48" height="48" alt="benostein" title="benostein"/></a> <a href="https://github.com/elliotsecops"><img src="https://avatars.githubusercontent.com/u/141947839?v=4&s=48" width="48" height="48" alt="elliotsecops" title="elliotsecops"/></a> <a href="https://github.com/christianklotz"><img src="https://avatars.githubusercontent.com/u/69443?v=4&s=48" width="48" height="48" alt="christianklotz" title="christianklotz"/></a> <a href="https://github.com/Nachx639"><img src="https://avatars.githubusercontent.com/u/71144023?v=4&s=48" width="48" height="48" alt="nachx639" title="nachx639"/></a> <a href="https://github.com/pvoo"><img src="https://avatars.githubusercontent.com/u/20116814?v=4&s=48" width="48" height="48" alt="pvoo" title="pvoo"/></a> <a href="https://github.com/sreekaransrinath"><img src="https://avatars.githubusercontent.com/u/50989977?v=4&s=48" width="48" height="48" alt="sreekaransrinath" title="sreekaransrinath"/></a>
|
||||
<a href="https://github.com/gupsammy"><img src="https://avatars.githubusercontent.com/u/20296019?v=4&s=48" width="48" height="48" alt="gupsammy" title="gupsammy"/></a> <a href="https://github.com/cristip73"><img src="https://avatars.githubusercontent.com/u/24499421?v=4&s=48" width="48" height="48" alt="cristip73" title="cristip73"/></a> <a href="https://github.com/stefangalescu"><img src="https://avatars.githubusercontent.com/u/52995748?v=4&s=48" width="48" height="48" alt="stefangalescu" title="stefangalescu"/></a> <a href="https://github.com/nachoiacovino"><img src="https://avatars.githubusercontent.com/u/50103937?v=4&s=48" width="48" height="48" alt="nachoiacovino" title="nachoiacovino"/></a> <a href="https://github.com/vsabavat"><img src="https://avatars.githubusercontent.com/u/50385532?v=4&s=48" width="48" height="48" alt="Vasanth Rao Naik Sabavat" title="Vasanth Rao Naik Sabavat"/></a> <a href="https://github.com/petter-b"><img src="https://avatars.githubusercontent.com/u/62076402?v=4&s=48" width="48" height="48" alt="petter-b" title="petter-b"/></a> <a href="https://github.com/thewilloftheshadow"><img src="https://avatars.githubusercontent.com/u/35580099?v=4&s=48" width="48" height="48" alt="thewilloftheshadow" title="thewilloftheshadow"/></a> <a href="https://github.com/leszekszpunar"><img src="https://avatars.githubusercontent.com/u/13106764?v=4&s=48" width="48" height="48" alt="leszekszpunar" title="leszekszpunar"/></a> <a href="https://github.com/scald"><img src="https://avatars.githubusercontent.com/u/1215913?v=4&s=48" width="48" height="48" alt="scald" title="scald"/></a> <a href="https://github.com/andranik-sahakyan"><img src="https://avatars.githubusercontent.com/u/8908029?v=4&s=48" width="48" height="48" alt="andranik-sahakyan" title="andranik-sahakyan"/></a>
|
||||
<a href="https://github.com/davidguttman"><img src="https://avatars.githubusercontent.com/u/431696?v=4&s=48" width="48" height="48" alt="davidguttman" title="davidguttman"/></a> <a href="https://github.com/sleontenko"><img src="https://avatars.githubusercontent.com/u/7135949?v=4&s=48" width="48" height="48" alt="sleontenko" title="sleontenko"/></a> <a href="https://github.com/denysvitali"><img src="https://avatars.githubusercontent.com/u/4939519?v=4&s=48" width="48" height="48" alt="denysvitali" title="denysvitali"/></a> <a href="https://github.com/sircrumpet"><img src="https://avatars.githubusercontent.com/u/4436535?v=4&s=48" width="48" height="48" alt="sircrumpet" title="sircrumpet"/></a> <a href="https://github.com/peschee"><img src="https://avatars.githubusercontent.com/u/63866?v=4&s=48" width="48" height="48" alt="peschee" title="peschee"/></a> <a href="https://github.com/nonggialiang"><img src="https://avatars.githubusercontent.com/u/14367839?v=4&s=48" width="48" height="48" alt="nonggialiang" title="nonggialiang"/></a> <a href="https://github.com/rafaelreis-r"><img src="https://avatars.githubusercontent.com/u/57492577?v=4&s=48" width="48" height="48" alt="rafaelreis-r" title="rafaelreis-r"/></a> <a href="https://github.com/dominicnunez"><img src="https://avatars.githubusercontent.com/u/43616264?v=4&s=48" width="48" height="48" alt="dominicnunez" title="dominicnunez"/></a> <a href="https://github.com/lploc94"><img src="https://avatars.githubusercontent.com/u/28453843?v=4&s=48" width="48" height="48" alt="lploc94" title="lploc94"/></a> <a href="https://github.com/ratulsarna"><img src="https://avatars.githubusercontent.com/u/105903728?v=4&s=48" width="48" height="48" alt="ratulsarna" title="ratulsarna"/></a>
|
||||
<a href="https://github.com/sfo2001"><img src="https://avatars.githubusercontent.com/u/103369858?v=4&s=48" width="48" height="48" alt="sfo2001" title="sfo2001"/></a> <a href="https://github.com/lutr0"><img src="https://avatars.githubusercontent.com/u/76906369?v=4&s=48" width="48" height="48" alt="lutr0" title="lutr0"/></a> <a href="https://github.com/kiranjd"><img src="https://avatars.githubusercontent.com/u/25822851?v=4&s=48" width="48" height="48" alt="kiranjd" title="kiranjd"/></a> <a href="https://github.com/danielz1z"><img src="https://avatars.githubusercontent.com/u/235270390?v=4&s=48" width="48" height="48" alt="danielz1z" title="danielz1z"/></a> <a href="https://github.com/AdeboyeDN"><img src="https://avatars.githubusercontent.com/u/65312338?v=4&s=48" width="48" height="48" alt="AdeboyeDN" title="AdeboyeDN"/></a> <a href="https://github.com/Alg0rix"><img src="https://avatars.githubusercontent.com/u/53804949?v=4&s=48" width="48" height="48" alt="Alg0rix" title="Alg0rix"/></a> <a href="https://github.com/Takhoffman"><img src="https://avatars.githubusercontent.com/u/781889?v=4&s=48" width="48" height="48" alt="Takhoffman" title="Takhoffman"/></a> <a href="https://github.com/papago2355"><img src="https://avatars.githubusercontent.com/u/68721273?v=4&s=48" width="48" height="48" alt="papago2355" title="papago2355"/></a> <a href="https://github.com/apps/clawdinator"><img src="https://avatars.githubusercontent.com/in/2607181?v=4&s=48" width="48" height="48" alt="clawdinator[bot]" title="clawdinator[bot]"/></a> <a href="https://github.com/emanuelst"><img src="https://avatars.githubusercontent.com/u/9994339?v=4&s=48" width="48" height="48" alt="emanuelst" title="emanuelst"/></a>
|
||||
<a href="https://github.com/evanotero"><img src="https://avatars.githubusercontent.com/u/13204105?v=4&s=48" width="48" height="48" alt="evanotero" title="evanotero"/></a> <a href="https://github.com/KristijanJovanovski"><img src="https://avatars.githubusercontent.com/u/8942284?v=4&s=48" width="48" height="48" alt="KristijanJovanovski" title="KristijanJovanovski"/></a> <a href="https://github.com/jlowin"><img src="https://avatars.githubusercontent.com/u/153965?v=4&s=48" width="48" height="48" alt="jlowin" title="jlowin"/></a> <a href="https://github.com/rdev"><img src="https://avatars.githubusercontent.com/u/8418866?v=4&s=48" width="48" height="48" alt="rdev" title="rdev"/></a> <a href="https://github.com/rhuanssauro"><img src="https://avatars.githubusercontent.com/u/164682191?v=4&s=48" width="48" height="48" alt="rhuanssauro" title="rhuanssauro"/></a> <a href="https://github.com/joshrad-dev"><img src="https://avatars.githubusercontent.com/u/62785552?v=4&s=48" width="48" height="48" alt="joshrad-dev" title="joshrad-dev"/></a> <a href="https://github.com/obviyus"><img src="https://avatars.githubusercontent.com/u/22031114?v=4&s=48" width="48" height="48" alt="obviyus" title="obviyus"/></a> <a href="https://github.com/osolmaz"><img src="https://avatars.githubusercontent.com/u/2453968?v=4&s=48" width="48" height="48" alt="osolmaz" title="osolmaz"/></a> <a href="https://github.com/adityashaw2"><img src="https://avatars.githubusercontent.com/u/41204444?v=4&s=48" width="48" height="48" alt="adityashaw2" title="adityashaw2"/></a> <a href="https://github.com/CashWilliams"><img src="https://avatars.githubusercontent.com/u/613573?v=4&s=48" width="48" height="48" alt="CashWilliams" title="CashWilliams"/></a>
|
||||
<a href="https://github.com/search?q=sheeek"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="sheeek" title="sheeek"/></a> <a href="https://github.com/ryancontent"><img src="https://avatars.githubusercontent.com/u/39743613?v=4&s=48" width="48" height="48" alt="ryancontent" title="ryancontent"/></a> <a href="https://github.com/jasonsschin"><img src="https://avatars.githubusercontent.com/u/1456889?v=4&s=48" width="48" height="48" alt="jasonsschin" title="jasonsschin"/></a> <a href="https://github.com/artuskg"><img src="https://avatars.githubusercontent.com/u/11966157?v=4&s=48" width="48" height="48" alt="artuskg" title="artuskg"/></a> <a href="https://github.com/onutc"><img src="https://avatars.githubusercontent.com/u/152018508?v=4&s=48" width="48" height="48" alt="onutc" title="onutc"/></a> <a href="https://github.com/pauloportella"><img src="https://avatars.githubusercontent.com/u/22947229?v=4&s=48" width="48" height="48" alt="pauloportella" title="pauloportella"/></a> <a href="https://github.com/HirokiKobayashi-R"><img src="https://avatars.githubusercontent.com/u/37167840?v=4&s=48" width="48" height="48" alt="HirokiKobayashi-R" title="HirokiKobayashi-R"/></a> <a href="https://github.com/ThanhNguyxn"><img src="https://avatars.githubusercontent.com/u/74597207?v=4&s=48" width="48" height="48" alt="ThanhNguyxn" title="ThanhNguyxn"/></a> <a href="https://github.com/kimitaka"><img src="https://avatars.githubusercontent.com/u/167225?v=4&s=48" width="48" height="48" alt="kimitaka" title="kimitaka"/></a> <a href="https://github.com/yuting0624"><img src="https://avatars.githubusercontent.com/u/32728916?v=4&s=48" width="48" height="48" alt="yuting0624" title="yuting0624"/></a>
|
||||
<a href="https://github.com/neooriginal"><img src="https://avatars.githubusercontent.com/u/54811660?v=4&s=48" width="48" height="48" alt="neooriginal" title="neooriginal"/></a> <a href="https://github.com/ManuelHettich"><img src="https://avatars.githubusercontent.com/u/17690367?v=4&s=48" width="48" height="48" alt="manuelhettich" title="manuelhettich"/></a> <a href="https://github.com/minghinmatthewlam"><img src="https://avatars.githubusercontent.com/u/14224566?v=4&s=48" width="48" height="48" alt="minghinmatthewlam" title="minghinmatthewlam"/></a> <a href="https://github.com/baccula"><img src="https://avatars.githubusercontent.com/u/22080883?v=4&s=48" width="48" height="48" alt="baccula" title="baccula"/></a> <a href="https://github.com/manikv12"><img src="https://avatars.githubusercontent.com/u/49544491?v=4&s=48" width="48" height="48" alt="manikv12" title="manikv12"/></a> <a href="https://github.com/myfunc"><img src="https://avatars.githubusercontent.com/u/19294627?v=4&s=48" width="48" height="48" alt="myfunc" title="myfunc"/></a> <a href="https://github.com/travisirby"><img src="https://avatars.githubusercontent.com/u/5958376?v=4&s=48" width="48" height="48" alt="travisirby" title="travisirby"/></a> <a href="https://github.com/buddyh"><img src="https://avatars.githubusercontent.com/u/31752869?v=4&s=48" width="48" height="48" alt="buddyh" title="buddyh"/></a> <a href="https://github.com/connorshea"><img src="https://avatars.githubusercontent.com/u/2977353?v=4&s=48" width="48" height="48" alt="connorshea" title="connorshea"/></a> <a href="https://github.com/kyleok"><img src="https://avatars.githubusercontent.com/u/58307870?v=4&s=48" width="48" height="48" alt="kyleok" title="kyleok"/></a>
|
||||
<a href="https://github.com/mcinteerj"><img src="https://avatars.githubusercontent.com/u/3613653?v=4&s=48" width="48" height="48" alt="mcinteerj" title="mcinteerj"/></a> <a href="https://github.com/apps/dependabot"><img src="https://avatars.githubusercontent.com/in/29110?v=4&s=48" width="48" height="48" alt="dependabot[bot]" title="dependabot[bot]"/></a> <a href="https://github.com/amitbiswal007"><img src="https://avatars.githubusercontent.com/u/108086198?v=4&s=48" width="48" height="48" alt="amitbiswal007" title="amitbiswal007"/></a> <a href="https://github.com/John-Rood"><img src="https://avatars.githubusercontent.com/u/62669593?v=4&s=48" width="48" height="48" alt="John-Rood" title="John-Rood"/></a> <a href="https://github.com/timkrase"><img src="https://avatars.githubusercontent.com/u/38947626?v=4&s=48" width="48" height="48" alt="timkrase" title="timkrase"/></a> <a href="https://github.com/uos-status"><img src="https://avatars.githubusercontent.com/u/255712580?v=4&s=48" width="48" height="48" alt="uos-status" title="uos-status"/></a> <a href="https://github.com/gerardward2007"><img src="https://avatars.githubusercontent.com/u/3002155?v=4&s=48" width="48" height="48" alt="gerardward2007" title="gerardward2007"/></a> <a href="https://github.com/roshanasingh4"><img src="https://avatars.githubusercontent.com/u/88576930?v=4&s=48" width="48" height="48" alt="roshanasingh4" title="roshanasingh4"/></a> <a href="https://github.com/tosh-hamburg"><img src="https://avatars.githubusercontent.com/u/58424326?v=4&s=48" width="48" height="48" alt="tosh-hamburg" title="tosh-hamburg"/></a> <a href="https://github.com/azade-c"><img src="https://avatars.githubusercontent.com/u/252790079?v=4&s=48" width="48" height="48" alt="azade-c" title="azade-c"/></a>
|
||||
<a href="https://github.com/badlogic"><img src="https://avatars.githubusercontent.com/u/514052?v=4&s=48" width="48" height="48" alt="badlogic" title="badlogic"/></a> <a href="https://github.com/dlauer"><img src="https://avatars.githubusercontent.com/u/757041?v=4&s=48" width="48" height="48" alt="dlauer" title="dlauer"/></a> <a href="https://github.com/JonUleis"><img src="https://avatars.githubusercontent.com/u/7644941?v=4&s=48" width="48" height="48" alt="JonUleis" title="JonUleis"/></a> <a href="https://github.com/shivamraut101"><img src="https://avatars.githubusercontent.com/u/110457469?v=4&s=48" width="48" height="48" alt="shivamraut101" title="shivamraut101"/></a> <a href="https://github.com/bjesuiter"><img src="https://avatars.githubusercontent.com/u/2365676?v=4&s=48" width="48" height="48" alt="bjesuiter" title="bjesuiter"/></a> <a href="https://github.com/cheeeee"><img src="https://avatars.githubusercontent.com/u/21245729?v=4&s=48" width="48" height="48" alt="cheeeee" title="cheeeee"/></a> <a href="https://github.com/robbyczgw-cla"><img src="https://avatars.githubusercontent.com/u/239660374?v=4&s=48" width="48" height="48" alt="robbyczgw-cla" title="robbyczgw-cla"/></a> <a href="https://github.com/YuriNachos"><img src="https://avatars.githubusercontent.com/u/19365375?v=4&s=48" width="48" height="48" alt="YuriNachos" title="YuriNachos"/></a> <a href="https://github.com/j1philli"><img src="https://avatars.githubusercontent.com/u/3744255?v=4&s=48" width="48" height="48" alt="Josh Phillips" title="Josh Phillips"/></a> <a href="https://github.com/pookNast"><img src="https://avatars.githubusercontent.com/u/14242552?v=4&s=48" width="48" height="48" alt="pookNast" title="pookNast"/></a>
|
||||
<a href="https://github.com/Whoaa512"><img src="https://avatars.githubusercontent.com/u/1581943?v=4&s=48" width="48" height="48" alt="Whoaa512" title="Whoaa512"/></a> <a href="https://github.com/chriseidhof"><img src="https://avatars.githubusercontent.com/u/5382?v=4&s=48" width="48" height="48" alt="chriseidhof" title="chriseidhof"/></a> <a href="https://github.com/ngutman"><img src="https://avatars.githubusercontent.com/u/1540134?v=4&s=48" width="48" height="48" alt="ngutman" title="ngutman"/></a> <a href="https://github.com/ysqander"><img src="https://avatars.githubusercontent.com/u/80843820?v=4&s=48" width="48" height="48" alt="ysqander" title="ysqander"/></a> <a href="https://github.com/search?q=Yurii%20Chukhlib"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="Yurii Chukhlib" title="Yurii Chukhlib"/></a> <a href="https://github.com/aj47"><img src="https://avatars.githubusercontent.com/u/8023513?v=4&s=48" width="48" height="48" alt="aj47" title="aj47"/></a> <a href="https://github.com/kennyklee"><img src="https://avatars.githubusercontent.com/u/1432489?v=4&s=48" width="48" height="48" alt="kennyklee" title="kennyklee"/></a> <a href="https://github.com/superman32432432"><img src="https://avatars.githubusercontent.com/u/7228420?v=4&s=48" width="48" height="48" alt="superman32432432" title="superman32432432"/></a> <a href="https://github.com/grp06"><img src="https://avatars.githubusercontent.com/u/1573959?v=4&s=48" width="48" height="48" alt="grp06" title="grp06"/></a> <a href="https://github.com/Hisleren"><img src="https://avatars.githubusercontent.com/u/83217244?v=4&s=48" width="48" height="48" alt="Hisleren" title="Hisleren"/></a>
|
||||
<a href="https://github.com/shatner"><img src="https://avatars.githubusercontent.com/u/17735435?v=4&s=48" width="48" height="48" alt="shatner" title="shatner"/></a> <a href="https://github.com/antons"><img src="https://avatars.githubusercontent.com/u/129705?v=4&s=48" width="48" height="48" alt="antons" title="antons"/></a> <a href="https://github.com/austinm911"><img src="https://avatars.githubusercontent.com/u/31991302?v=4&s=48" width="48" height="48" alt="austinm911" title="austinm911"/></a> <a href="https://github.com/apps/blacksmith-sh"><img src="https://avatars.githubusercontent.com/in/807020?v=4&s=48" width="48" height="48" alt="blacksmith-sh[bot]" title="blacksmith-sh[bot]"/></a> <a href="https://github.com/damoahdominic"><img src="https://avatars.githubusercontent.com/u/4623434?v=4&s=48" width="48" height="48" alt="damoahdominic" title="damoahdominic"/></a> <a href="https://github.com/dan-dr"><img src="https://avatars.githubusercontent.com/u/6669808?v=4&s=48" width="48" height="48" alt="dan-dr" title="dan-dr"/></a> <a href="https://github.com/GHesericsu"><img src="https://avatars.githubusercontent.com/u/60202455?v=4&s=48" width="48" height="48" alt="GHesericsu" title="GHesericsu"/></a> <a href="https://github.com/HeimdallStrategy"><img src="https://avatars.githubusercontent.com/u/223014405?v=4&s=48" width="48" height="48" alt="HeimdallStrategy" title="HeimdallStrategy"/></a> <a href="https://github.com/imfing"><img src="https://avatars.githubusercontent.com/u/5097752?v=4&s=48" width="48" height="48" alt="imfing" title="imfing"/></a> <a href="https://github.com/jalehman"><img src="https://avatars.githubusercontent.com/u/550978?v=4&s=48" width="48" height="48" alt="jalehman" title="jalehman"/></a>
|
||||
<a href="https://github.com/jarvis-medmatic"><img src="https://avatars.githubusercontent.com/u/252428873?v=4&s=48" width="48" height="48" alt="jarvis-medmatic" title="jarvis-medmatic"/></a> <a href="https://github.com/kkarimi"><img src="https://avatars.githubusercontent.com/u/875218?v=4&s=48" width="48" height="48" alt="kkarimi" title="kkarimi"/></a> <a href="https://github.com/mahmoudashraf93"><img src="https://avatars.githubusercontent.com/u/9130129?v=4&s=48" width="48" height="48" alt="mahmoudashraf93" title="mahmoudashraf93"/></a> <a href="https://github.com/pkrmf"><img src="https://avatars.githubusercontent.com/u/1714267?v=4&s=48" width="48" height="48" alt="pkrmf" title="pkrmf"/></a> <a href="https://github.com/RandyVentures"><img src="https://avatars.githubusercontent.com/u/149904821?v=4&s=48" width="48" height="48" alt="RandyVentures" title="RandyVentures"/></a> <a href="https://github.com/robhparker"><img src="https://avatars.githubusercontent.com/u/7404740?v=4&s=48" width="48" height="48" alt="robhparker" title="robhparker"/></a> <a href="https://github.com/search?q=Ryan%20Lisse"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="Ryan Lisse" title="Ryan Lisse"/></a> <a href="https://github.com/dougvk"><img src="https://avatars.githubusercontent.com/u/401660?v=4&s=48" width="48" height="48" alt="dougvk" title="dougvk"/></a> <a href="https://github.com/erikpr1994"><img src="https://avatars.githubusercontent.com/u/6299331?v=4&s=48" width="48" height="48" alt="erikpr1994" title="erikpr1994"/></a> <a href="https://github.com/fal3"><img src="https://avatars.githubusercontent.com/u/6484295?v=4&s=48" width="48" height="48" alt="fal3" title="fal3"/></a>
|
||||
<a href="https://github.com/search?q=Ghost"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="Ghost" title="Ghost"/></a> <a href="https://github.com/jonasjancarik"><img src="https://avatars.githubusercontent.com/u/2459191?v=4&s=48" width="48" height="48" alt="jonasjancarik" title="jonasjancarik"/></a> <a href="https://github.com/search?q=Keith%20the%20Silly%20Goose"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="Keith the Silly Goose" title="Keith the Silly Goose"/></a> <a href="https://github.com/search?q=L36%20Server"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="L36 Server" title="L36 Server"/></a> <a href="https://github.com/search?q=Marc"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="Marc" title="Marc"/></a> <a href="https://github.com/mitschabaude-bot"><img src="https://avatars.githubusercontent.com/u/247582884?v=4&s=48" width="48" height="48" alt="mitschabaude-bot" title="mitschabaude-bot"/></a> <a href="https://github.com/mkbehr"><img src="https://avatars.githubusercontent.com/u/1285?v=4&s=48" width="48" height="48" alt="mkbehr" title="mkbehr"/></a> <a href="https://github.com/neist"><img src="https://avatars.githubusercontent.com/u/1029724?v=4&s=48" width="48" height="48" alt="neist" title="neist"/></a> <a href="https://github.com/sibbl"><img src="https://avatars.githubusercontent.com/u/866535?v=4&s=48" width="48" height="48" alt="sibbl" title="sibbl"/></a> <a href="https://github.com/abhijeet117"><img src="https://avatars.githubusercontent.com/u/192859219?v=4&s=48" width="48" height="48" alt="abhijeet117" title="abhijeet117"/></a>
|
||||
<a href="https://github.com/chrisrodz"><img src="https://avatars.githubusercontent.com/u/2967620?v=4&s=48" width="48" height="48" alt="chrisrodz" title="chrisrodz"/></a> <a href="https://github.com/search?q=Friederike%20Seiler"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="Friederike Seiler" title="Friederike Seiler"/></a> <a href="https://github.com/gabriel-trigo"><img src="https://avatars.githubusercontent.com/u/38991125?v=4&s=48" width="48" height="48" alt="gabriel-trigo" title="gabriel-trigo"/></a> <a href="https://github.com/Iamadig"><img src="https://avatars.githubusercontent.com/u/102129234?v=4&s=48" width="48" height="48" alt="iamadig" title="iamadig"/></a> <a href="https://github.com/itsjling"><img src="https://avatars.githubusercontent.com/u/2521993?v=4&s=48" width="48" height="48" alt="itsjling" title="itsjling"/></a> <a href="https://github.com/jdrhyne"><img src="https://avatars.githubusercontent.com/u/7828464?v=4&s=48" width="48" height="48" alt="Jonathan D. Rhyne (DJ-D)" title="Jonathan D. Rhyne (DJ-D)"/></a> <a href="https://github.com/search?q=Joshua%20Mitchell"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="Joshua Mitchell" title="Joshua Mitchell"/></a> <a href="https://github.com/search?q=Kit"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="Kit" title="Kit"/></a> <a href="https://github.com/koala73"><img src="https://avatars.githubusercontent.com/u/996596?v=4&s=48" width="48" height="48" alt="koala73" title="koala73"/></a> <a href="https://github.com/manmal"><img src="https://avatars.githubusercontent.com/u/142797?v=4&s=48" width="48" height="48" alt="manmal" title="manmal"/></a>
|
||||
<a href="https://github.com/steipete"><img src="https://avatars.githubusercontent.com/u/58493?v=4&s=48" width="48" height="48" alt="steipete" title="steipete"/></a> <a href="https://github.com/joshp123"><img src="https://avatars.githubusercontent.com/u/1497361?v=4&s=48" width="48" height="48" alt="joshp123" title="joshp123"/></a> <a href="https://github.com/cpojer"><img src="https://avatars.githubusercontent.com/u/13352?v=4&s=48" width="48" height="48" alt="cpojer" title="cpojer"/></a> <a href="https://github.com/mbelinky"><img src="https://avatars.githubusercontent.com/u/132747814?v=4&s=48" width="48" height="48" alt="Mariano Belinky" title="Mariano Belinky"/></a> <a href="https://github.com/plum-dawg"><img src="https://avatars.githubusercontent.com/u/5909950?v=4&s=48" width="48" height="48" alt="plum-dawg" title="plum-dawg"/></a> <a href="https://github.com/bohdanpodvirnyi"><img src="https://avatars.githubusercontent.com/u/31819391?v=4&s=48" width="48" height="48" alt="bohdanpodvirnyi" title="bohdanpodvirnyi"/></a> <a href="https://github.com/iHildy"><img src="https://avatars.githubusercontent.com/u/25069719?v=4&s=48" width="48" height="48" alt="iHildy" title="iHildy"/></a> <a href="https://github.com/jaydenfyi"><img src="https://avatars.githubusercontent.com/u/213395523?v=4&s=48" width="48" height="48" alt="jaydenfyi" title="jaydenfyi"/></a> <a href="https://github.com/joaohlisboa"><img src="https://avatars.githubusercontent.com/u/8200873?v=4&s=48" width="48" height="48" alt="joaohlisboa" title="joaohlisboa"/></a> <a href="https://github.com/mneves75"><img src="https://avatars.githubusercontent.com/u/2423436?v=4&s=48" width="48" height="48" alt="mneves75" title="mneves75"/></a>
|
||||
<a href="https://github.com/MatthieuBizien"><img src="https://avatars.githubusercontent.com/u/173090?v=4&s=48" width="48" height="48" alt="MatthieuBizien" title="MatthieuBizien"/></a> <a href="https://github.com/MaudeBot"><img src="https://avatars.githubusercontent.com/u/255777700?v=4&s=48" width="48" height="48" alt="MaudeBot" title="MaudeBot"/></a> <a href="https://github.com/sebslight"><img src="https://avatars.githubusercontent.com/u/19554889?v=4&s=48" width="48" height="48" alt="sebslight" title="sebslight"/></a> <a href="https://github.com/Glucksberg"><img src="https://avatars.githubusercontent.com/u/80581902?v=4&s=48" width="48" height="48" alt="Glucksberg" title="Glucksberg"/></a> <a href="https://github.com/rahthakor"><img src="https://avatars.githubusercontent.com/u/8470553?v=4&s=48" width="48" height="48" alt="rahthakor" title="rahthakor"/></a> <a href="https://github.com/vrknetha"><img src="https://avatars.githubusercontent.com/u/20596261?v=4&s=48" width="48" height="48" alt="vrknetha" title="vrknetha"/></a> <a href="https://github.com/tyler6204"><img src="https://avatars.githubusercontent.com/u/64381258?v=4&s=48" width="48" height="48" alt="tyler6204" title="tyler6204"/></a> <a href="https://github.com/vignesh07"><img src="https://avatars.githubusercontent.com/u/1436853?v=4&s=48" width="48" height="48" alt="vignesh07" title="vignesh07"/></a> <a href="https://github.com/radek-paclt"><img src="https://avatars.githubusercontent.com/u/50451445?v=4&s=48" width="48" height="48" alt="radek-paclt" title="radek-paclt"/></a> <a href="https://github.com/tobiasbischoff"><img src="https://avatars.githubusercontent.com/u/711564?v=4&s=48" width="48" height="48" alt="Tobias Bischoff" title="Tobias Bischoff"/></a>
|
||||
<a href="https://github.com/czekaj"><img src="https://avatars.githubusercontent.com/u/1464539?v=4&s=48" width="48" height="48" alt="czekaj" title="czekaj"/></a> <a href="https://github.com/ethanpalm"><img src="https://avatars.githubusercontent.com/u/56270045?v=4&s=48" width="48" height="48" alt="ethanpalm" title="ethanpalm"/></a> <a href="https://github.com/mukhtharcm"><img src="https://avatars.githubusercontent.com/u/56378562?v=4&s=48" width="48" height="48" alt="mukhtharcm" title="mukhtharcm"/></a> <a href="https://github.com/maxsumrall"><img src="https://avatars.githubusercontent.com/u/628843?v=4&s=48" width="48" height="48" alt="maxsumrall" title="maxsumrall"/></a> <a href="https://github.com/xadenryan"><img src="https://avatars.githubusercontent.com/u/165437834?v=4&s=48" width="48" height="48" alt="xadenryan" title="xadenryan"/></a> <a href="https://github.com/VACInc"><img src="https://avatars.githubusercontent.com/u/3279061?v=4&s=48" width="48" height="48" alt="VACInc" title="VACInc"/></a> <a href="https://github.com/rodrigouroz"><img src="https://avatars.githubusercontent.com/u/384037?v=4&s=48" width="48" height="48" alt="rodrigouroz" title="rodrigouroz"/></a> <a href="https://github.com/juanpablodlc"><img src="https://avatars.githubusercontent.com/u/92012363?v=4&s=48" width="48" height="48" alt="juanpablodlc" title="juanpablodlc"/></a> <a href="https://github.com/conroywhitney"><img src="https://avatars.githubusercontent.com/u/249891?v=4&s=48" width="48" height="48" alt="conroywhitney" title="conroywhitney"/></a> <a href="https://github.com/hsrvc"><img src="https://avatars.githubusercontent.com/u/129702169?v=4&s=48" width="48" height="48" alt="hsrvc" title="hsrvc"/></a>
|
||||
<a href="https://github.com/christianklotz"><img src="https://avatars.githubusercontent.com/u/69443?v=4&s=48" width="48" height="48" alt="christianklotz" title="christianklotz"/></a> <a href="https://github.com/magimetal"><img src="https://avatars.githubusercontent.com/u/36491250?v=4&s=48" width="48" height="48" alt="magimetal" title="magimetal"/></a> <a href="https://github.com/zerone0x"><img src="https://avatars.githubusercontent.com/u/39543393?v=4&s=48" width="48" height="48" alt="zerone0x" title="zerone0x"/></a> <a href="https://github.com/meaningfool"><img src="https://avatars.githubusercontent.com/u/2862331?v=4&s=48" width="48" height="48" alt="meaningfool" title="meaningfool"/></a> <a href="https://github.com/Takhoffman"><img src="https://avatars.githubusercontent.com/u/781889?v=4&s=48" width="48" height="48" alt="Takhoffman" title="Takhoffman"/></a> <a href="https://github.com/patelhiren"><img src="https://avatars.githubusercontent.com/u/172098?v=4&s=48" width="48" height="48" alt="patelhiren" title="patelhiren"/></a> <a href="https://github.com/NicholasSpisak"><img src="https://avatars.githubusercontent.com/u/129075147?v=4&s=48" width="48" height="48" alt="NicholasSpisak" title="NicholasSpisak"/></a> <a href="https://github.com/jonisjongithub"><img src="https://avatars.githubusercontent.com/u/86072337?v=4&s=48" width="48" height="48" alt="jonisjongithub" title="jonisjongithub"/></a> <a href="https://github.com/AbhisekBasu1"><img src="https://avatars.githubusercontent.com/u/40645221?v=4&s=48" width="48" height="48" alt="abhisekbasu1" title="abhisekbasu1"/></a> <a href="https://github.com/jamesgroat"><img src="https://avatars.githubusercontent.com/u/2634024?v=4&s=48" width="48" height="48" alt="jamesgroat" title="jamesgroat"/></a>
|
||||
<a href="https://github.com/BunsDev"><img src="https://avatars.githubusercontent.com/u/68980965?v=4&s=48" width="48" height="48" alt="BunsDev" title="BunsDev"/></a> <a href="https://github.com/claude"><img src="https://avatars.githubusercontent.com/u/81847?v=4&s=48" width="48" height="48" alt="claude" title="claude"/></a> <a href="https://github.com/JustYannicc"><img src="https://avatars.githubusercontent.com/u/52761674?v=4&s=48" width="48" height="48" alt="JustYannicc" title="JustYannicc"/></a> <a href="https://github.com/Hyaxia"><img src="https://avatars.githubusercontent.com/u/36747317?v=4&s=48" width="48" height="48" alt="Hyaxia" title="Hyaxia"/></a> <a href="https://github.com/dantelex"><img src="https://avatars.githubusercontent.com/u/631543?v=4&s=48" width="48" height="48" alt="dantelex" title="dantelex"/></a> <a href="https://github.com/SocialNerd42069"><img src="https://avatars.githubusercontent.com/u/118244303?v=4&s=48" width="48" height="48" alt="SocialNerd42069" title="SocialNerd42069"/></a> <a href="https://github.com/daveonkels"><img src="https://avatars.githubusercontent.com/u/533642?v=4&s=48" width="48" height="48" alt="daveonkels" title="daveonkels"/></a> <a href="https://github.com/apps/google-labs-jules"><img src="https://avatars.githubusercontent.com/in/842251?v=4&s=48" width="48" height="48" alt="google-labs-jules[bot]" title="google-labs-jules[bot]"/></a> <a href="https://github.com/lc0rp"><img src="https://avatars.githubusercontent.com/u/2609441?v=4&s=48" width="48" height="48" alt="lc0rp" title="lc0rp"/></a> <a href="https://github.com/mousberg"><img src="https://avatars.githubusercontent.com/u/57605064?v=4&s=48" width="48" height="48" alt="mousberg" title="mousberg"/></a>
|
||||
<a href="https://github.com/adam91holt"><img src="https://avatars.githubusercontent.com/u/9592417?v=4&s=48" width="48" height="48" alt="adam91holt" title="adam91holt"/></a> <a href="https://github.com/hougangdev"><img src="https://avatars.githubusercontent.com/u/105773686?v=4&s=48" width="48" height="48" alt="hougangdev" title="hougangdev"/></a> <a href="https://github.com/gumadeiras"><img src="https://avatars.githubusercontent.com/u/5599352?v=4&s=48" width="48" height="48" alt="gumadeiras" title="gumadeiras"/></a> <a href="https://github.com/shakkernerd"><img src="https://avatars.githubusercontent.com/u/165377636?v=4&s=48" width="48" height="48" alt="shakkernerd" title="shakkernerd"/></a> <a href="https://github.com/mteam88"><img src="https://avatars.githubusercontent.com/u/84196639?v=4&s=48" width="48" height="48" alt="mteam88" title="mteam88"/></a> <a href="https://github.com/hirefrank"><img src="https://avatars.githubusercontent.com/u/183158?v=4&s=48" width="48" height="48" alt="hirefrank" title="hirefrank"/></a> <a href="https://github.com/joeynyc"><img src="https://avatars.githubusercontent.com/u/17919866?v=4&s=48" width="48" height="48" alt="joeynyc" title="joeynyc"/></a> <a href="https://github.com/orlyjamie"><img src="https://avatars.githubusercontent.com/u/6668807?v=4&s=48" width="48" height="48" alt="orlyjamie" title="orlyjamie"/></a> <a href="https://github.com/dbhurley"><img src="https://avatars.githubusercontent.com/u/5251425?v=4&s=48" width="48" height="48" alt="dbhurley" title="dbhurley"/></a> <a href="https://github.com/omniwired"><img src="https://avatars.githubusercontent.com/u/322761?v=4&s=48" width="48" height="48" alt="Eng. Juan Combetto" title="Eng. Juan Combetto"/></a>
|
||||
<a href="https://github.com/TSavo"><img src="https://avatars.githubusercontent.com/u/877990?v=4&s=48" width="48" height="48" alt="TSavo" title="TSavo"/></a> <a href="https://github.com/aerolalit"><img src="https://avatars.githubusercontent.com/u/17166039?v=4&s=48" width="48" height="48" alt="aerolalit" title="aerolalit"/></a> <a href="https://github.com/julianengel"><img src="https://avatars.githubusercontent.com/u/10634231?v=4&s=48" width="48" height="48" alt="julianengel" title="julianengel"/></a> <a href="https://github.com/bradleypriest"><img src="https://avatars.githubusercontent.com/u/167215?v=4&s=48" width="48" height="48" alt="bradleypriest" title="bradleypriest"/></a> <a href="https://github.com/benithors"><img src="https://avatars.githubusercontent.com/u/20652882?v=4&s=48" width="48" height="48" alt="benithors" title="benithors"/></a> <a href="https://github.com/rohannagpal"><img src="https://avatars.githubusercontent.com/u/4009239?v=4&s=48" width="48" height="48" alt="rohannagpal" title="rohannagpal"/></a> <a href="https://github.com/timolins"><img src="https://avatars.githubusercontent.com/u/1440854?v=4&s=48" width="48" height="48" alt="timolins" title="timolins"/></a> <a href="https://github.com/f-trycua"><img src="https://avatars.githubusercontent.com/u/195596869?v=4&s=48" width="48" height="48" alt="f-trycua" title="f-trycua"/></a> <a href="https://github.com/benostein"><img src="https://avatars.githubusercontent.com/u/31802821?v=4&s=48" width="48" height="48" alt="benostein" title="benostein"/></a> <a href="https://github.com/elliotsecops"><img src="https://avatars.githubusercontent.com/u/141947839?v=4&s=48" width="48" height="48" alt="elliotsecops" title="elliotsecops"/></a>
|
||||
<a href="https://github.com/Nachx639"><img src="https://avatars.githubusercontent.com/u/71144023?v=4&s=48" width="48" height="48" alt="nachx639" title="nachx639"/></a> <a href="https://github.com/pvoo"><img src="https://avatars.githubusercontent.com/u/20116814?v=4&s=48" width="48" height="48" alt="pvoo" title="pvoo"/></a> <a href="https://github.com/sreekaransrinath"><img src="https://avatars.githubusercontent.com/u/50989977?v=4&s=48" width="48" height="48" alt="sreekaransrinath" title="sreekaransrinath"/></a> <a href="https://github.com/gupsammy"><img src="https://avatars.githubusercontent.com/u/20296019?v=4&s=48" width="48" height="48" alt="gupsammy" title="gupsammy"/></a> <a href="https://github.com/cristip73"><img src="https://avatars.githubusercontent.com/u/24499421?v=4&s=48" width="48" height="48" alt="cristip73" title="cristip73"/></a> <a href="https://github.com/stefangalescu"><img src="https://avatars.githubusercontent.com/u/52995748?v=4&s=48" width="48" height="48" alt="stefangalescu" title="stefangalescu"/></a> <a href="https://github.com/nachoiacovino"><img src="https://avatars.githubusercontent.com/u/50103937?v=4&s=48" width="48" height="48" alt="nachoiacovino" title="nachoiacovino"/></a> <a href="https://github.com/vsabavat"><img src="https://avatars.githubusercontent.com/u/50385532?v=4&s=48" width="48" height="48" alt="Vasanth Rao Naik Sabavat" title="Vasanth Rao Naik Sabavat"/></a> <a href="https://github.com/petter-b"><img src="https://avatars.githubusercontent.com/u/62076402?v=4&s=48" width="48" height="48" alt="petter-b" title="petter-b"/></a> <a href="https://github.com/thewilloftheshadow"><img src="https://avatars.githubusercontent.com/u/35580099?v=4&s=48" width="48" height="48" alt="thewilloftheshadow" title="thewilloftheshadow"/></a>
|
||||
<a href="https://github.com/leszekszpunar"><img src="https://avatars.githubusercontent.com/u/13106764?v=4&s=48" width="48" height="48" alt="leszekszpunar" title="leszekszpunar"/></a> <a href="https://github.com/scald"><img src="https://avatars.githubusercontent.com/u/1215913?v=4&s=48" width="48" height="48" alt="scald" title="scald"/></a> <a href="https://github.com/andranik-sahakyan"><img src="https://avatars.githubusercontent.com/u/8908029?v=4&s=48" width="48" height="48" alt="andranik-sahakyan" title="andranik-sahakyan"/></a> <a href="https://github.com/davidguttman"><img src="https://avatars.githubusercontent.com/u/431696?v=4&s=48" width="48" height="48" alt="davidguttman" title="davidguttman"/></a> <a href="https://github.com/sleontenko"><img src="https://avatars.githubusercontent.com/u/7135949?v=4&s=48" width="48" height="48" alt="sleontenko" title="sleontenko"/></a> <a href="https://github.com/denysvitali"><img src="https://avatars.githubusercontent.com/u/4939519?v=4&s=48" width="48" height="48" alt="denysvitali" title="denysvitali"/></a> <a href="https://github.com/apps/clawdinator"><img src="https://avatars.githubusercontent.com/in/2607181?v=4&s=48" width="48" height="48" alt="clawdinator[bot]" title="clawdinator[bot]"/></a> <a href="https://github.com/sircrumpet"><img src="https://avatars.githubusercontent.com/u/4436535?v=4&s=48" width="48" height="48" alt="sircrumpet" title="sircrumpet"/></a> <a href="https://github.com/peschee"><img src="https://avatars.githubusercontent.com/u/63866?v=4&s=48" width="48" height="48" alt="peschee" title="peschee"/></a> <a href="https://github.com/davidiach"><img src="https://avatars.githubusercontent.com/u/28102235?v=4&s=48" width="48" height="48" alt="davidiach" title="davidiach"/></a>
|
||||
<a href="https://github.com/nonggialiang"><img src="https://avatars.githubusercontent.com/u/14367839?v=4&s=48" width="48" height="48" alt="nonggialiang" title="nonggialiang"/></a> <a href="https://github.com/rafaelreis-r"><img src="https://avatars.githubusercontent.com/u/57492577?v=4&s=48" width="48" height="48" alt="rafaelreis-r" title="rafaelreis-r"/></a> <a href="https://github.com/dominicnunez"><img src="https://avatars.githubusercontent.com/u/43616264?v=4&s=48" width="48" height="48" alt="dominicnunez" title="dominicnunez"/></a> <a href="https://github.com/lploc94"><img src="https://avatars.githubusercontent.com/u/28453843?v=4&s=48" width="48" height="48" alt="lploc94" title="lploc94"/></a> <a href="https://github.com/ratulsarna"><img src="https://avatars.githubusercontent.com/u/105903728?v=4&s=48" width="48" height="48" alt="ratulsarna" title="ratulsarna"/></a> <a href="https://github.com/sfo2001"><img src="https://avatars.githubusercontent.com/u/103369858?v=4&s=48" width="48" height="48" alt="sfo2001" title="sfo2001"/></a> <a href="https://github.com/lutr0"><img src="https://avatars.githubusercontent.com/u/76906369?v=4&s=48" width="48" height="48" alt="lutr0" title="lutr0"/></a> <a href="https://github.com/kiranjd"><img src="https://avatars.githubusercontent.com/u/25822851?v=4&s=48" width="48" height="48" alt="kiranjd" title="kiranjd"/></a> <a href="https://github.com/danielz1z"><img src="https://avatars.githubusercontent.com/u/235270390?v=4&s=48" width="48" height="48" alt="danielz1z" title="danielz1z"/></a> <a href="https://github.com/Iranb"><img src="https://avatars.githubusercontent.com/u/49674669?v=4&s=48" width="48" height="48" alt="Iranb" title="Iranb"/></a>
|
||||
<a href="https://github.com/AdeboyeDN"><img src="https://avatars.githubusercontent.com/u/65312338?v=4&s=48" width="48" height="48" alt="AdeboyeDN" title="AdeboyeDN"/></a> <a href="https://github.com/Alg0rix"><img src="https://avatars.githubusercontent.com/u/53804949?v=4&s=48" width="48" height="48" alt="Alg0rix" title="Alg0rix"/></a> <a href="https://github.com/obviyus"><img src="https://avatars.githubusercontent.com/u/22031114?v=4&s=48" width="48" height="48" alt="obviyus" title="obviyus"/></a> <a href="https://github.com/papago2355"><img src="https://avatars.githubusercontent.com/u/68721273?v=4&s=48" width="48" height="48" alt="papago2355" title="papago2355"/></a> <a href="https://github.com/emanuelst"><img src="https://avatars.githubusercontent.com/u/9994339?v=4&s=48" width="48" height="48" alt="emanuelst" title="emanuelst"/></a> <a href="https://github.com/evanotero"><img src="https://avatars.githubusercontent.com/u/13204105?v=4&s=48" width="48" height="48" alt="evanotero" title="evanotero"/></a> <a href="https://github.com/KristijanJovanovski"><img src="https://avatars.githubusercontent.com/u/8942284?v=4&s=48" width="48" height="48" alt="KristijanJovanovski" title="KristijanJovanovski"/></a> <a href="https://github.com/jlowin"><img src="https://avatars.githubusercontent.com/u/153965?v=4&s=48" width="48" height="48" alt="jlowin" title="jlowin"/></a> <a href="https://github.com/rdev"><img src="https://avatars.githubusercontent.com/u/8418866?v=4&s=48" width="48" height="48" alt="rdev" title="rdev"/></a> <a href="https://github.com/rhuanssauro"><img src="https://avatars.githubusercontent.com/u/164682191?v=4&s=48" width="48" height="48" alt="rhuanssauro" title="rhuanssauro"/></a>
|
||||
<a href="https://github.com/joshrad-dev"><img src="https://avatars.githubusercontent.com/u/62785552?v=4&s=48" width="48" height="48" alt="joshrad-dev" title="joshrad-dev"/></a> <a href="https://github.com/osolmaz"><img src="https://avatars.githubusercontent.com/u/2453968?v=4&s=48" width="48" height="48" alt="osolmaz" title="osolmaz"/></a> <a href="https://github.com/adityashaw2"><img src="https://avatars.githubusercontent.com/u/41204444?v=4&s=48" width="48" height="48" alt="adityashaw2" title="adityashaw2"/></a> <a href="https://github.com/CashWilliams"><img src="https://avatars.githubusercontent.com/u/613573?v=4&s=48" width="48" height="48" alt="CashWilliams" title="CashWilliams"/></a> <a href="https://github.com/search?q=sheeek"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="sheeek" title="sheeek"/></a> <a href="https://github.com/ryancontent"><img src="https://avatars.githubusercontent.com/u/39743613?v=4&s=48" width="48" height="48" alt="ryancontent" title="ryancontent"/></a> <a href="https://github.com/jasonsschin"><img src="https://avatars.githubusercontent.com/u/1456889?v=4&s=48" width="48" height="48" alt="jasonsschin" title="jasonsschin"/></a> <a href="https://github.com/artuskg"><img src="https://avatars.githubusercontent.com/u/11966157?v=4&s=48" width="48" height="48" alt="artuskg" title="artuskg"/></a> <a href="https://github.com/onutc"><img src="https://avatars.githubusercontent.com/u/152018508?v=4&s=48" width="48" height="48" alt="onutc" title="onutc"/></a> <a href="https://github.com/pauloportella"><img src="https://avatars.githubusercontent.com/u/22947229?v=4&s=48" width="48" height="48" alt="pauloportella" title="pauloportella"/></a>
|
||||
<a href="https://github.com/HirokiKobayashi-R"><img src="https://avatars.githubusercontent.com/u/37167840?v=4&s=48" width="48" height="48" alt="HirokiKobayashi-R" title="HirokiKobayashi-R"/></a> <a href="https://github.com/ThanhNguyxn"><img src="https://avatars.githubusercontent.com/u/74597207?v=4&s=48" width="48" height="48" alt="ThanhNguyxn" title="ThanhNguyxn"/></a> <a href="https://github.com/kimitaka"><img src="https://avatars.githubusercontent.com/u/167225?v=4&s=48" width="48" height="48" alt="kimitaka" title="kimitaka"/></a> <a href="https://github.com/yuting0624"><img src="https://avatars.githubusercontent.com/u/32728916?v=4&s=48" width="48" height="48" alt="yuting0624" title="yuting0624"/></a> <a href="https://github.com/neooriginal"><img src="https://avatars.githubusercontent.com/u/54811660?v=4&s=48" width="48" height="48" alt="neooriginal" title="neooriginal"/></a> <a href="https://github.com/ManuelHettich"><img src="https://avatars.githubusercontent.com/u/17690367?v=4&s=48" width="48" height="48" alt="manuelhettich" title="manuelhettich"/></a> <a href="https://github.com/minghinmatthewlam"><img src="https://avatars.githubusercontent.com/u/14224566?v=4&s=48" width="48" height="48" alt="minghinmatthewlam" title="minghinmatthewlam"/></a> <a href="https://github.com/baccula"><img src="https://avatars.githubusercontent.com/u/22080883?v=4&s=48" width="48" height="48" alt="baccula" title="baccula"/></a> <a href="https://github.com/manikv12"><img src="https://avatars.githubusercontent.com/u/49544491?v=4&s=48" width="48" height="48" alt="manikv12" title="manikv12"/></a> <a href="https://github.com/myfunc"><img src="https://avatars.githubusercontent.com/u/19294627?v=4&s=48" width="48" height="48" alt="myfunc" title="myfunc"/></a>
|
||||
<a href="https://github.com/travisirby"><img src="https://avatars.githubusercontent.com/u/5958376?v=4&s=48" width="48" height="48" alt="travisirby" title="travisirby"/></a> <a href="https://github.com/buddyh"><img src="https://avatars.githubusercontent.com/u/31752869?v=4&s=48" width="48" height="48" alt="buddyh" title="buddyh"/></a> <a href="https://github.com/connorshea"><img src="https://avatars.githubusercontent.com/u/2977353?v=4&s=48" width="48" height="48" alt="connorshea" title="connorshea"/></a> <a href="https://github.com/bjesuiter"><img src="https://avatars.githubusercontent.com/u/2365676?v=4&s=48" width="48" height="48" alt="bjesuiter" title="bjesuiter"/></a> <a href="https://github.com/kyleok"><img src="https://avatars.githubusercontent.com/u/58307870?v=4&s=48" width="48" height="48" alt="kyleok" title="kyleok"/></a> <a href="https://github.com/mcinteerj"><img src="https://avatars.githubusercontent.com/u/3613653?v=4&s=48" width="48" height="48" alt="mcinteerj" title="mcinteerj"/></a> <a href="https://github.com/badlogic"><img src="https://avatars.githubusercontent.com/u/514052?v=4&s=48" width="48" height="48" alt="badlogic" title="badlogic"/></a> <a href="https://github.com/apps/dependabot"><img src="https://avatars.githubusercontent.com/in/29110?v=4&s=48" width="48" height="48" alt="dependabot[bot]" title="dependabot[bot]"/></a> <a href="https://github.com/amitbiswal007"><img src="https://avatars.githubusercontent.com/u/108086198?v=4&s=48" width="48" height="48" alt="amitbiswal007" title="amitbiswal007"/></a> <a href="https://github.com/John-Rood"><img src="https://avatars.githubusercontent.com/u/62669593?v=4&s=48" width="48" height="48" alt="John-Rood" title="John-Rood"/></a>
|
||||
<a href="https://github.com/timkrase"><img src="https://avatars.githubusercontent.com/u/38947626?v=4&s=48" width="48" height="48" alt="timkrase" title="timkrase"/></a> <a href="https://github.com/uos-status"><img src="https://avatars.githubusercontent.com/u/255712580?v=4&s=48" width="48" height="48" alt="uos-status" title="uos-status"/></a> <a href="https://github.com/gerardward2007"><img src="https://avatars.githubusercontent.com/u/3002155?v=4&s=48" width="48" height="48" alt="gerardward2007" title="gerardward2007"/></a> <a href="https://github.com/roshanasingh4"><img src="https://avatars.githubusercontent.com/u/88576930?v=4&s=48" width="48" height="48" alt="roshanasingh4" title="roshanasingh4"/></a> <a href="https://github.com/tosh-hamburg"><img src="https://avatars.githubusercontent.com/u/58424326?v=4&s=48" width="48" height="48" alt="tosh-hamburg" title="tosh-hamburg"/></a> <a href="https://github.com/azade-c"><img src="https://avatars.githubusercontent.com/u/252790079?v=4&s=48" width="48" height="48" alt="azade-c" title="azade-c"/></a> <a href="https://github.com/dlauer"><img src="https://avatars.githubusercontent.com/u/757041?v=4&s=48" width="48" height="48" alt="dlauer" title="dlauer"/></a> <a href="https://github.com/JonUleis"><img src="https://avatars.githubusercontent.com/u/7644941?v=4&s=48" width="48" height="48" alt="JonUleis" title="JonUleis"/></a> <a href="https://github.com/shivamraut101"><img src="https://avatars.githubusercontent.com/u/110457469?v=4&s=48" width="48" height="48" alt="shivamraut101" title="shivamraut101"/></a> <a href="https://github.com/cheeeee"><img src="https://avatars.githubusercontent.com/u/21245729?v=4&s=48" width="48" height="48" alt="cheeeee" title="cheeeee"/></a>
|
||||
<a href="https://github.com/robbyczgw-cla"><img src="https://avatars.githubusercontent.com/u/239660374?v=4&s=48" width="48" height="48" alt="robbyczgw-cla" title="robbyczgw-cla"/></a> <a href="https://github.com/YuriNachos"><img src="https://avatars.githubusercontent.com/u/19365375?v=4&s=48" width="48" height="48" alt="YuriNachos" title="YuriNachos"/></a> <a href="https://github.com/j1philli"><img src="https://avatars.githubusercontent.com/u/3744255?v=4&s=48" width="48" height="48" alt="Josh Phillips" title="Josh Phillips"/></a> <a href="https://github.com/Wangnov"><img src="https://avatars.githubusercontent.com/u/48670012?v=4&s=48" width="48" height="48" alt="Wangnov" title="Wangnov"/></a> <a href="https://github.com/kaizen403"><img src="https://avatars.githubusercontent.com/u/134706404?v=4&s=48" width="48" height="48" alt="kaizen403" title="kaizen403"/></a> <a href="https://github.com/pookNast"><img src="https://avatars.githubusercontent.com/u/14242552?v=4&s=48" width="48" height="48" alt="pookNast" title="pookNast"/></a> <a href="https://github.com/Whoaa512"><img src="https://avatars.githubusercontent.com/u/1581943?v=4&s=48" width="48" height="48" alt="Whoaa512" title="Whoaa512"/></a> <a href="https://github.com/chriseidhof"><img src="https://avatars.githubusercontent.com/u/5382?v=4&s=48" width="48" height="48" alt="chriseidhof" title="chriseidhof"/></a> <a href="https://github.com/ngutman"><img src="https://avatars.githubusercontent.com/u/1540134?v=4&s=48" width="48" height="48" alt="ngutman" title="ngutman"/></a> <a href="https://github.com/ysqander"><img src="https://avatars.githubusercontent.com/u/80843820?v=4&s=48" width="48" height="48" alt="ysqander" title="ysqander"/></a>
|
||||
<a href="https://github.com/search?q=Yurii%20Chukhlib"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="Yurii Chukhlib" title="Yurii Chukhlib"/></a> <a href="https://github.com/aj47"><img src="https://avatars.githubusercontent.com/u/8023513?v=4&s=48" width="48" height="48" alt="aj47" title="aj47"/></a> <a href="https://github.com/kennyklee"><img src="https://avatars.githubusercontent.com/u/1432489?v=4&s=48" width="48" height="48" alt="kennyklee" title="kennyklee"/></a> <a href="https://github.com/superman32432432"><img src="https://avatars.githubusercontent.com/u/7228420?v=4&s=48" width="48" height="48" alt="superman32432432" title="superman32432432"/></a> <a href="https://github.com/grp06"><img src="https://avatars.githubusercontent.com/u/1573959?v=4&s=48" width="48" height="48" alt="grp06" title="grp06"/></a> <a href="https://github.com/Hisleren"><img src="https://avatars.githubusercontent.com/u/83217244?v=4&s=48" width="48" height="48" alt="Hisleren" title="Hisleren"/></a> <a href="https://github.com/shatner"><img src="https://avatars.githubusercontent.com/u/17735435?v=4&s=48" width="48" height="48" alt="shatner" title="shatner"/></a> <a href="https://github.com/antons"><img src="https://avatars.githubusercontent.com/u/129705?v=4&s=48" width="48" height="48" alt="antons" title="antons"/></a> <a href="https://github.com/austinm911"><img src="https://avatars.githubusercontent.com/u/31991302?v=4&s=48" width="48" height="48" alt="austinm911" title="austinm911"/></a> <a href="https://github.com/apps/blacksmith-sh"><img src="https://avatars.githubusercontent.com/in/807020?v=4&s=48" width="48" height="48" alt="blacksmith-sh[bot]" title="blacksmith-sh[bot]"/></a>
|
||||
<a href="https://github.com/damoahdominic"><img src="https://avatars.githubusercontent.com/u/4623434?v=4&s=48" width="48" height="48" alt="damoahdominic" title="damoahdominic"/></a> <a href="https://github.com/dan-dr"><img src="https://avatars.githubusercontent.com/u/6669808?v=4&s=48" width="48" height="48" alt="dan-dr" title="dan-dr"/></a> <a href="https://github.com/GHesericsu"><img src="https://avatars.githubusercontent.com/u/60202455?v=4&s=48" width="48" height="48" alt="GHesericsu" title="GHesericsu"/></a> <a href="https://github.com/HeimdallStrategy"><img src="https://avatars.githubusercontent.com/u/223014405?v=4&s=48" width="48" height="48" alt="HeimdallStrategy" title="HeimdallStrategy"/></a> <a href="https://github.com/imfing"><img src="https://avatars.githubusercontent.com/u/5097752?v=4&s=48" width="48" height="48" alt="imfing" title="imfing"/></a> <a href="https://github.com/jalehman"><img src="https://avatars.githubusercontent.com/u/550978?v=4&s=48" width="48" height="48" alt="jalehman" title="jalehman"/></a> <a href="https://github.com/jarvis-medmatic"><img src="https://avatars.githubusercontent.com/u/252428873?v=4&s=48" width="48" height="48" alt="jarvis-medmatic" title="jarvis-medmatic"/></a> <a href="https://github.com/kkarimi"><img src="https://avatars.githubusercontent.com/u/875218?v=4&s=48" width="48" height="48" alt="kkarimi" title="kkarimi"/></a> <a href="https://github.com/Lukavyi"><img src="https://avatars.githubusercontent.com/u/1013690?v=4&s=48" width="48" height="48" alt="Lukavyi" title="Lukavyi"/></a> <a href="https://github.com/mahmoudashraf93"><img src="https://avatars.githubusercontent.com/u/9130129?v=4&s=48" width="48" height="48" alt="mahmoudashraf93" title="mahmoudashraf93"/></a>
|
||||
<a href="https://github.com/pkrmf"><img src="https://avatars.githubusercontent.com/u/1714267?v=4&s=48" width="48" height="48" alt="pkrmf" title="pkrmf"/></a> <a href="https://github.com/RandyVentures"><img src="https://avatars.githubusercontent.com/u/149904821?v=4&s=48" width="48" height="48" alt="RandyVentures" title="RandyVentures"/></a> <a href="https://github.com/robhparker"><img src="https://avatars.githubusercontent.com/u/7404740?v=4&s=48" width="48" height="48" alt="robhparker" title="robhparker"/></a> <a href="https://github.com/search?q=Ryan%20Lisse"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="Ryan Lisse" title="Ryan Lisse"/></a> <a href="https://github.com/Yeom-JinHo"><img src="https://avatars.githubusercontent.com/u/81306489?v=4&s=48" width="48" height="48" alt="Yeom-JinHo" title="Yeom-JinHo"/></a> <a href="https://github.com/dougvk"><img src="https://avatars.githubusercontent.com/u/401660?v=4&s=48" width="48" height="48" alt="dougvk" title="dougvk"/></a> <a href="https://github.com/erikpr1994"><img src="https://avatars.githubusercontent.com/u/6299331?v=4&s=48" width="48" height="48" alt="erikpr1994" title="erikpr1994"/></a> <a href="https://github.com/fal3"><img src="https://avatars.githubusercontent.com/u/6484295?v=4&s=48" width="48" height="48" alt="fal3" title="fal3"/></a> <a href="https://github.com/search?q=Ghost"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="Ghost" title="Ghost"/></a> <a href="https://github.com/jonasjancarik"><img src="https://avatars.githubusercontent.com/u/2459191?v=4&s=48" width="48" height="48" alt="jonasjancarik" title="jonasjancarik"/></a>
|
||||
<a href="https://github.com/search?q=Keith%20the%20Silly%20Goose"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="Keith the Silly Goose" title="Keith the Silly Goose"/></a> <a href="https://github.com/search?q=L36%20Server"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="L36 Server" title="L36 Server"/></a> <a href="https://github.com/search?q=Marc"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="Marc" title="Marc"/></a> <a href="https://github.com/mitschabaude-bot"><img src="https://avatars.githubusercontent.com/u/247582884?v=4&s=48" width="48" height="48" alt="mitschabaude-bot" title="mitschabaude-bot"/></a> <a href="https://github.com/mkbehr"><img src="https://avatars.githubusercontent.com/u/1285?v=4&s=48" width="48" height="48" alt="mkbehr" title="mkbehr"/></a> <a href="https://github.com/neist"><img src="https://avatars.githubusercontent.com/u/1029724?v=4&s=48" width="48" height="48" alt="neist" title="neist"/></a> <a href="https://github.com/sibbl"><img src="https://avatars.githubusercontent.com/u/866535?v=4&s=48" width="48" height="48" alt="sibbl" title="sibbl"/></a> <a href="https://github.com/abhijeet117"><img src="https://avatars.githubusercontent.com/u/192859219?v=4&s=48" width="48" height="48" alt="abhijeet117" title="abhijeet117"/></a> <a href="https://github.com/chrisrodz"><img src="https://avatars.githubusercontent.com/u/2967620?v=4&s=48" width="48" height="48" alt="chrisrodz" title="chrisrodz"/></a> <a href="https://github.com/search?q=Friederike%20Seiler"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="Friederike Seiler" title="Friederike Seiler"/></a>
|
||||
<a href="https://github.com/gabriel-trigo"><img src="https://avatars.githubusercontent.com/u/38991125?v=4&s=48" width="48" height="48" alt="gabriel-trigo" title="gabriel-trigo"/></a> <a href="https://github.com/Iamadig"><img src="https://avatars.githubusercontent.com/u/102129234?v=4&s=48" width="48" height="48" alt="iamadig" title="iamadig"/></a> <a href="https://github.com/itsjling"><img src="https://avatars.githubusercontent.com/u/2521993?v=4&s=48" width="48" height="48" alt="itsjling" title="itsjling"/></a> <a href="https://github.com/jdrhyne"><img src="https://avatars.githubusercontent.com/u/7828464?v=4&s=48" width="48" height="48" alt="Jonathan D. Rhyne (DJ-D)" title="Jonathan D. Rhyne (DJ-D)"/></a> <a href="https://github.com/search?q=Joshua%20Mitchell"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="Joshua Mitchell" title="Joshua Mitchell"/></a> <a href="https://github.com/kelvinCB"><img src="https://avatars.githubusercontent.com/u/50544379?v=4&s=48" width="48" height="48" alt="kelvinCB" title="kelvinCB"/></a> <a href="https://github.com/search?q=Kit"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="Kit" title="Kit"/></a> <a href="https://github.com/koala73"><img src="https://avatars.githubusercontent.com/u/996596?v=4&s=48" width="48" height="48" alt="koala73" title="koala73"/></a> <a href="https://github.com/manmal"><img src="https://avatars.githubusercontent.com/u/142797?v=4&s=48" width="48" height="48" alt="manmal" title="manmal"/></a> <a href="https://github.com/mitsuhiko"><img src="https://avatars.githubusercontent.com/u/7396?v=4&s=48" width="48" height="48" alt="mitsuhiko" title="mitsuhiko"/></a>
|
||||
<a href="https://github.com/ogulcancelik"><img src="https://avatars.githubusercontent.com/u/7064011?v=4&s=48" width="48" height="48" alt="ogulcancelik" title="ogulcancelik"/></a> <a href="https://github.com/pasogott"><img src="https://avatars.githubusercontent.com/u/23458152?v=4&s=48" width="48" height="48" alt="pasogott" title="pasogott"/></a> <a href="https://github.com/petradonka"><img src="https://avatars.githubusercontent.com/u/7353770?v=4&s=48" width="48" height="48" alt="petradonka" title="petradonka"/></a> <a href="https://github.com/rubyrunsstuff"><img src="https://avatars.githubusercontent.com/u/246602379?v=4&s=48" width="48" height="48" alt="rubyrunsstuff" title="rubyrunsstuff"/></a> <a href="https://github.com/siddhantjain"><img src="https://avatars.githubusercontent.com/u/4835232?v=4&s=48" width="48" height="48" alt="siddhantjain" title="siddhantjain"/></a> <a href="https://github.com/spiceoogway"><img src="https://avatars.githubusercontent.com/u/105812383?v=4&s=48" width="48" height="48" alt="spiceoogway" title="spiceoogway"/></a> <a href="https://github.com/suminhthanh"><img src="https://avatars.githubusercontent.com/u/2907636?v=4&s=48" width="48" height="48" alt="suminhthanh" title="suminhthanh"/></a> <a href="https://github.com/svkozak"><img src="https://avatars.githubusercontent.com/u/31941359?v=4&s=48" width="48" height="48" alt="svkozak" title="svkozak"/></a> <a href="https://github.com/wes-davis"><img src="https://avatars.githubusercontent.com/u/16506720?v=4&s=48" width="48" height="48" alt="wes-davis" title="wes-davis"/></a> <a href="https://github.com/zats"><img src="https://avatars.githubusercontent.com/u/2688806?v=4&s=48" width="48" height="48" alt="zats" title="zats"/></a>
|
||||
<a href="https://github.com/24601"><img src="https://avatars.githubusercontent.com/u/1157207?v=4&s=48" width="48" height="48" alt="24601" title="24601"/></a> <a href="https://github.com/ameno-"><img src="https://avatars.githubusercontent.com/u/2416135?v=4&s=48" width="48" height="48" alt="ameno-" title="ameno-"/></a> <a href="https://github.com/bonald"><img src="https://avatars.githubusercontent.com/u/12394874?v=4&s=48" width="48" height="48" alt="bonald" title="bonald"/></a> <a href="https://github.com/bravostation"><img src="https://avatars.githubusercontent.com/u/257991910?v=4&s=48" width="48" height="48" alt="bravostation" title="bravostation"/></a> <a href="https://github.com/search?q=Chris%20Taylor"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="Chris Taylor" title="Chris Taylor"/></a> <a href="https://github.com/dguido"><img src="https://avatars.githubusercontent.com/u/294844?v=4&s=48" width="48" height="48" alt="dguido" title="dguido"/></a> <a href="https://github.com/djangonavarro220"><img src="https://avatars.githubusercontent.com/u/251162586?v=4&s=48" width="48" height="48" alt="Django Navarro" title="Django Navarro"/></a> <a href="https://github.com/evalexpr"><img src="https://avatars.githubusercontent.com/u/23485511?v=4&s=48" width="48" height="48" alt="evalexpr" title="evalexpr"/></a> <a href="https://github.com/henrino3"><img src="https://avatars.githubusercontent.com/u/4260288?v=4&s=48" width="48" height="48" alt="henrino3" title="henrino3"/></a> <a href="https://github.com/humanwritten"><img src="https://avatars.githubusercontent.com/u/206531610?v=4&s=48" width="48" height="48" alt="humanwritten" title="humanwritten"/></a>
|
||||
<a href="https://github.com/larlyssa"><img src="https://avatars.githubusercontent.com/u/13128869?v=4&s=48" width="48" height="48" alt="larlyssa" title="larlyssa"/></a> <a href="https://github.com/Lukavyi"><img src="https://avatars.githubusercontent.com/u/1013690?v=4&s=48" width="48" height="48" alt="Lukavyi" title="Lukavyi"/></a> <a href="https://github.com/mitsuhiko"><img src="https://avatars.githubusercontent.com/u/7396?v=4&s=48" width="48" height="48" alt="mitsuhiko" title="mitsuhiko"/></a> <a href="https://github.com/odysseus0"><img src="https://avatars.githubusercontent.com/u/8635094?v=4&s=48" width="48" height="48" alt="odysseus0" title="odysseus0"/></a> <a href="https://github.com/oswalpalash"><img src="https://avatars.githubusercontent.com/u/6431196?v=4&s=48" width="48" height="48" alt="oswalpalash" title="oswalpalash"/></a> <a href="https://github.com/pcty-nextgen-service-account"><img src="https://avatars.githubusercontent.com/u/112553441?v=4&s=48" width="48" height="48" alt="pcty-nextgen-service-account" title="pcty-nextgen-service-account"/></a> <a href="https://github.com/pi0"><img src="https://avatars.githubusercontent.com/u/5158436?v=4&s=48" width="48" height="48" alt="pi0" title="pi0"/></a> <a href="https://github.com/rmorse"><img src="https://avatars.githubusercontent.com/u/853547?v=4&s=48" width="48" height="48" alt="rmorse" title="rmorse"/></a> <a href="https://github.com/search?q=Roopak%20Nijhara"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="Roopak Nijhara" title="Roopak Nijhara"/></a> <a href="https://github.com/Syhids"><img src="https://avatars.githubusercontent.com/u/671202?v=4&s=48" width="48" height="48" alt="Syhids" title="Syhids"/></a>
|
||||
<a href="https://github.com/search?q=Ubuntu"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="Ubuntu" title="Ubuntu"/></a> <a href="https://github.com/search?q=xiaose"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="xiaose" title="xiaose"/></a> <a href="https://github.com/search?q=Aaron%20Konyer"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="Aaron Konyer" title="Aaron Konyer"/></a> <a href="https://github.com/aaronveklabs"><img src="https://avatars.githubusercontent.com/u/225997828?v=4&s=48" width="48" height="48" alt="aaronveklabs" title="aaronveklabs"/></a> <a href="https://github.com/andreabadesso"><img src="https://avatars.githubusercontent.com/u/3586068?v=4&s=48" width="48" height="48" alt="andreabadesso" title="andreabadesso"/></a> <a href="https://github.com/search?q=Andrii"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="Andrii" title="Andrii"/></a> <a href="https://github.com/cash-echo-bot"><img src="https://avatars.githubusercontent.com/u/252747386?v=4&s=48" width="48" height="48" alt="cash-echo-bot" title="cash-echo-bot"/></a> <a href="https://github.com/search?q=Clawd"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="Clawd" title="Clawd"/></a> <a href="https://github.com/search?q=ClawdFx"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="ClawdFx" title="ClawdFx"/></a> <a href="https://github.com/danballance"><img src="https://avatars.githubusercontent.com/u/13839912?v=4&s=48" width="48" height="48" alt="danballance" title="danballance"/></a>
|
||||
<a href="https://github.com/EnzeD"><img src="https://avatars.githubusercontent.com/u/9866900?v=4&s=48" width="48" height="48" alt="EnzeD" title="EnzeD"/></a> <a href="https://github.com/erik-agens"><img src="https://avatars.githubusercontent.com/u/80908960?v=4&s=48" width="48" height="48" alt="erik-agens" title="erik-agens"/></a> <a href="https://github.com/Evizero"><img src="https://avatars.githubusercontent.com/u/10854026?v=4&s=48" width="48" height="48" alt="Evizero" title="Evizero"/></a> <a href="https://github.com/fcatuhe"><img src="https://avatars.githubusercontent.com/u/17382215?v=4&s=48" width="48" height="48" alt="fcatuhe" title="fcatuhe"/></a> <a href="https://github.com/itsjaydesu"><img src="https://avatars.githubusercontent.com/u/220390?v=4&s=48" width="48" height="48" alt="itsjaydesu" title="itsjaydesu"/></a> <a href="https://github.com/ivancasco"><img src="https://avatars.githubusercontent.com/u/2452858?v=4&s=48" width="48" height="48" alt="ivancasco" title="ivancasco"/></a> <a href="https://github.com/ivanrvpereira"><img src="https://avatars.githubusercontent.com/u/183991?v=4&s=48" width="48" height="48" alt="ivanrvpereira" title="ivanrvpereira"/></a> <a href="https://github.com/search?q=Jarvis"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="Jarvis" title="Jarvis"/></a> <a href="https://github.com/jayhickey"><img src="https://avatars.githubusercontent.com/u/1676460?v=4&s=48" width="48" height="48" alt="jayhickey" title="jayhickey"/></a> <a href="https://github.com/jeffersonwarrior"><img src="https://avatars.githubusercontent.com/u/89030989?v=4&s=48" width="48" height="48" alt="jeffersonwarrior" title="jeffersonwarrior"/></a>
|
||||
<a href="https://github.com/search?q=jeffersonwarrior"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="jeffersonwarrior" title="jeffersonwarrior"/></a> <a href="https://github.com/jverdi"><img src="https://avatars.githubusercontent.com/u/345050?v=4&s=48" width="48" height="48" alt="jverdi" title="jverdi"/></a> <a href="https://github.com/longmaba"><img src="https://avatars.githubusercontent.com/u/9361500?v=4&s=48" width="48" height="48" alt="longmaba" title="longmaba"/></a> <a href="https://github.com/MarvinCui"><img src="https://avatars.githubusercontent.com/u/130876763?v=4&s=48" width="48" height="48" alt="MarvinCui" title="MarvinCui"/></a> <a href="https://github.com/mjrussell"><img src="https://avatars.githubusercontent.com/u/1641895?v=4&s=48" width="48" height="48" alt="mjrussell" title="mjrussell"/></a> <a href="https://github.com/odnxe"><img src="https://avatars.githubusercontent.com/u/403141?v=4&s=48" width="48" height="48" alt="odnxe" title="odnxe"/></a> <a href="https://github.com/optimikelabs"><img src="https://avatars.githubusercontent.com/u/31423109?v=4&s=48" width="48" height="48" alt="optimikelabs" title="optimikelabs"/></a> <a href="https://github.com/p6l-richard"><img src="https://avatars.githubusercontent.com/u/18185649?v=4&s=48" width="48" height="48" alt="p6l-richard" title="p6l-richard"/></a> <a href="https://github.com/philipp-spiess"><img src="https://avatars.githubusercontent.com/u/458591?v=4&s=48" width="48" height="48" alt="philipp-spiess" title="philipp-spiess"/></a> <a href="https://github.com/search?q=Pocket%20Clawd"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="Pocket Clawd" title="Pocket Clawd"/></a>
|
||||
<a href="https://github.com/robaxelsen"><img src="https://avatars.githubusercontent.com/u/13132899?v=4&s=48" width="48" height="48" alt="robaxelsen" title="robaxelsen"/></a> <a href="https://github.com/search?q=Sash%20Catanzarite"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="Sash Catanzarite" title="Sash Catanzarite"/></a> <a href="https://github.com/Suksham-sharma"><img src="https://avatars.githubusercontent.com/u/94667656?v=4&s=48" width="48" height="48" alt="Suksham-sharma" title="Suksham-sharma"/></a> <a href="https://github.com/T5-AndyML"><img src="https://avatars.githubusercontent.com/u/22801233?v=4&s=48" width="48" height="48" alt="T5-AndyML" title="T5-AndyML"/></a> <a href="https://github.com/tewatia"><img src="https://avatars.githubusercontent.com/u/22875334?v=4&s=48" width="48" height="48" alt="tewatia" title="tewatia"/></a> <a href="https://github.com/thejhinvirtuoso"><img src="https://avatars.githubusercontent.com/u/258521837?v=4&s=48" width="48" height="48" alt="thejhinvirtuoso" title="thejhinvirtuoso"/></a> <a href="https://github.com/travisp"><img src="https://avatars.githubusercontent.com/u/165698?v=4&s=48" width="48" height="48" alt="travisp" title="travisp"/></a> <a href="https://github.com/search?q=VAC"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="VAC" title="VAC"/></a> <a href="https://github.com/search?q=william%20arzt"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="william arzt" title="william arzt"/></a> <a href="https://github.com/zknicker"><img src="https://avatars.githubusercontent.com/u/1164085?v=4&s=48" width="48" height="48" alt="zknicker" title="zknicker"/></a>
|
||||
<a href="https://github.com/0oAstro"><img src="https://avatars.githubusercontent.com/u/79555780?v=4&s=48" width="48" height="48" alt="0oAstro" title="0oAstro"/></a> <a href="https://github.com/abhaymundhara"><img src="https://avatars.githubusercontent.com/u/62872231?v=4&s=48" width="48" height="48" alt="abhaymundhara" title="abhaymundhara"/></a> <a href="https://github.com/aduk059"><img src="https://avatars.githubusercontent.com/u/257603478?v=4&s=48" width="48" height="48" alt="aduk059" title="aduk059"/></a> <a href="https://github.com/aldoeliacim"><img src="https://avatars.githubusercontent.com/u/17973757?v=4&s=48" width="48" height="48" alt="aldoeliacim" title="aldoeliacim"/></a> <a href="https://github.com/search?q=alejandro%20maza"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="alejandro maza" title="alejandro maza"/></a> <a href="https://github.com/Alex-Alaniz"><img src="https://avatars.githubusercontent.com/u/88956822?v=4&s=48" width="48" height="48" alt="Alex-Alaniz" title="Alex-Alaniz"/></a> <a href="https://github.com/alexanderatallah"><img src="https://avatars.githubusercontent.com/u/1011391?v=4&s=48" width="48" height="48" alt="alexanderatallah" title="alexanderatallah"/></a> <a href="https://github.com/alexstyl"><img src="https://avatars.githubusercontent.com/u/1665273?v=4&s=48" width="48" height="48" alt="alexstyl" title="alexstyl"/></a> <a href="https://github.com/andrewting19"><img src="https://avatars.githubusercontent.com/u/10536704?v=4&s=48" width="48" height="48" alt="andrewting19" title="andrewting19"/></a> <a href="https://github.com/anpoirier"><img src="https://avatars.githubusercontent.com/u/1245729?v=4&s=48" width="48" height="48" alt="anpoirier" title="anpoirier"/></a>
|
||||
<a href="https://github.com/araa47"><img src="https://avatars.githubusercontent.com/u/22760261?v=4&s=48" width="48" height="48" alt="araa47" title="araa47"/></a> <a href="https://github.com/arthyn"><img src="https://avatars.githubusercontent.com/u/5466421?v=4&s=48" width="48" height="48" alt="arthyn" title="arthyn"/></a> <a href="https://github.com/Asleep123"><img src="https://avatars.githubusercontent.com/u/122379135?v=4&s=48" width="48" height="48" alt="Asleep123" title="Asleep123"/></a> <a href="https://github.com/search?q=Ayush%20Ojha"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="Ayush Ojha" title="Ayush Ojha"/></a> <a href="https://github.com/Ayush10"><img src="https://avatars.githubusercontent.com/u/7945279?v=4&s=48" width="48" height="48" alt="Ayush10" title="Ayush10"/></a> <a href="https://github.com/bguidolim"><img src="https://avatars.githubusercontent.com/u/987360?v=4&s=48" width="48" height="48" alt="bguidolim" title="bguidolim"/></a> <a href="https://github.com/bolismauro"><img src="https://avatars.githubusercontent.com/u/771999?v=4&s=48" width="48" height="48" alt="bolismauro" title="bolismauro"/></a> <a href="https://github.com/championswimmer"><img src="https://avatars.githubusercontent.com/u/1327050?v=4&s=48" width="48" height="48" alt="championswimmer" title="championswimmer"/></a> <a href="https://github.com/chenyuan99"><img src="https://avatars.githubusercontent.com/u/25518100?v=4&s=48" width="48" height="48" alt="chenyuan99" title="chenyuan99"/></a> <a href="https://github.com/Chloe-VP"><img src="https://avatars.githubusercontent.com/u/257371598?v=4&s=48" width="48" height="48" alt="Chloe-VP" title="Chloe-VP"/></a>
|
||||
<a href="https://github.com/search?q=Clawdbot%20Maintainers"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="Clawdbot Maintainers" title="Clawdbot Maintainers"/></a> <a href="https://github.com/conhecendoia"><img src="https://avatars.githubusercontent.com/u/82890727?v=4&s=48" width="48" height="48" alt="conhecendoia" title="conhecendoia"/></a> <a href="https://github.com/dasilva333"><img src="https://avatars.githubusercontent.com/u/947827?v=4&s=48" width="48" height="48" alt="dasilva333" title="dasilva333"/></a> <a href="https://github.com/David-Marsh-Photo"><img src="https://avatars.githubusercontent.com/u/228404527?v=4&s=48" width="48" height="48" alt="David-Marsh-Photo" title="David-Marsh-Photo"/></a> <a href="https://github.com/search?q=Developer"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="Developer" title="Developer"/></a> <a href="https://github.com/search?q=Dimitrios%20Ploutarchos"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="Dimitrios Ploutarchos" title="Dimitrios Ploutarchos"/></a> <a href="https://github.com/search?q=Drake%20Thomsen"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="Drake Thomsen" title="Drake Thomsen"/></a> <a href="https://github.com/dylanneve1"><img src="https://avatars.githubusercontent.com/u/31746704?v=4&s=48" width="48" height="48" alt="dylanneve1" title="dylanneve1"/></a> <a href="https://github.com/search?q=Felix%20Krause"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="Felix Krause" title="Felix Krause"/></a> <a href="https://github.com/foeken"><img src="https://avatars.githubusercontent.com/u/13864?v=4&s=48" width="48" height="48" alt="foeken" title="foeken"/></a>
|
||||
<a href="https://github.com/frankekn"><img src="https://avatars.githubusercontent.com/u/4488090?v=4&s=48" width="48" height="48" alt="frankekn" title="frankekn"/></a> <a href="https://github.com/fredheir"><img src="https://avatars.githubusercontent.com/u/3304869?v=4&s=48" width="48" height="48" alt="fredheir" title="fredheir"/></a> <a href="https://github.com/search?q=ganghyun%20kim"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="ganghyun kim" title="ganghyun kim"/></a> <a href="https://github.com/grrowl"><img src="https://avatars.githubusercontent.com/u/907140?v=4&s=48" width="48" height="48" alt="grrowl" title="grrowl"/></a> <a href="https://github.com/gtsifrikas"><img src="https://avatars.githubusercontent.com/u/8904378?v=4&s=48" width="48" height="48" alt="gtsifrikas" title="gtsifrikas"/></a> <a href="https://github.com/HassanFleyah"><img src="https://avatars.githubusercontent.com/u/228002017?v=4&s=48" width="48" height="48" alt="HassanFleyah" title="HassanFleyah"/></a> <a href="https://github.com/HazAT"><img src="https://avatars.githubusercontent.com/u/363802?v=4&s=48" width="48" height="48" alt="HazAT" title="HazAT"/></a> <a href="https://github.com/hclsys"><img src="https://avatars.githubusercontent.com/u/7755017?v=4&s=48" width="48" height="48" alt="hclsys" title="hclsys"/></a> <a href="https://github.com/hrdwdmrbl"><img src="https://avatars.githubusercontent.com/u/554881?v=4&s=48" width="48" height="48" alt="hrdwdmrbl" title="hrdwdmrbl"/></a> <a href="https://github.com/hugobarauna"><img src="https://avatars.githubusercontent.com/u/2719?v=4&s=48" width="48" height="48" alt="hugobarauna" title="hugobarauna"/></a>
|
||||
<a href="https://github.com/iamEvanYT"><img src="https://avatars.githubusercontent.com/u/47493765?v=4&s=48" width="48" height="48" alt="iamEvanYT" title="iamEvanYT"/></a> <a href="https://github.com/search?q=Jamie%20Openshaw"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="Jamie Openshaw" title="Jamie Openshaw"/></a> <a href="https://github.com/search?q=Jane"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="Jane" title="Jane"/></a> <a href="https://github.com/search?q=Jarvis%20Deploy"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="Jarvis Deploy" title="Jarvis Deploy"/></a> <a href="https://github.com/search?q=Jefferson%20Nunn"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="Jefferson Nunn" title="Jefferson Nunn"/></a> <a href="https://github.com/jogi47"><img src="https://avatars.githubusercontent.com/u/1710139?v=4&s=48" width="48" height="48" alt="jogi47" title="jogi47"/></a> <a href="https://github.com/kentaro"><img src="https://avatars.githubusercontent.com/u/3458?v=4&s=48" width="48" height="48" alt="kentaro" title="kentaro"/></a> <a href="https://github.com/search?q=Kevin%20Lin"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="Kevin Lin" title="Kevin Lin"/></a> <a href="https://github.com/kira-ariaki"><img src="https://avatars.githubusercontent.com/u/257352493?v=4&s=48" width="48" height="48" alt="kira-ariaki" title="kira-ariaki"/></a> <a href="https://github.com/kitze"><img src="https://avatars.githubusercontent.com/u/1160594?v=4&s=48" width="48" height="48" alt="kitze" title="kitze"/></a>
|
||||
<a href="https://github.com/Kiwitwitter"><img src="https://avatars.githubusercontent.com/u/25277769?v=4&s=48" width="48" height="48" alt="Kiwitwitter" title="Kiwitwitter"/></a> <a href="https://github.com/levifig"><img src="https://avatars.githubusercontent.com/u/1605?v=4&s=48" width="48" height="48" alt="levifig" title="levifig"/></a> <a href="https://github.com/search?q=Lloyd"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="Lloyd" title="Lloyd"/></a> <a href="https://github.com/loganaden"><img src="https://avatars.githubusercontent.com/u/1688420?v=4&s=48" width="48" height="48" alt="loganaden" title="loganaden"/></a> <a href="https://github.com/longjos"><img src="https://avatars.githubusercontent.com/u/740160?v=4&s=48" width="48" height="48" alt="longjos" title="longjos"/></a> <a href="https://github.com/loukotal"><img src="https://avatars.githubusercontent.com/u/18210858?v=4&s=48" width="48" height="48" alt="loukotal" title="loukotal"/></a> <a href="https://github.com/louzhixian"><img src="https://avatars.githubusercontent.com/u/7994361?v=4&s=48" width="48" height="48" alt="louzhixian" title="louzhixian"/></a> <a href="https://github.com/martinpucik"><img src="https://avatars.githubusercontent.com/u/5503097?v=4&s=48" width="48" height="48" alt="martinpucik" title="martinpucik"/></a> <a href="https://github.com/search?q=Matt%20mini"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="Matt mini" title="Matt mini"/></a> <a href="https://github.com/mertcicekci0"><img src="https://avatars.githubusercontent.com/u/179321902?v=4&s=48" width="48" height="48" alt="mertcicekci0" title="mertcicekci0"/></a>
|
||||
<a href="https://github.com/search?q=Miles"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="Miles" title="Miles"/></a> <a href="https://github.com/mrdbstn"><img src="https://avatars.githubusercontent.com/u/58957632?v=4&s=48" width="48" height="48" alt="mrdbstn" title="mrdbstn"/></a> <a href="https://github.com/MSch"><img src="https://avatars.githubusercontent.com/u/7475?v=4&s=48" width="48" height="48" alt="MSch" title="MSch"/></a> <a href="https://github.com/search?q=Mustafa%20Tag%20Eldeen"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="Mustafa Tag Eldeen" title="Mustafa Tag Eldeen"/></a> <a href="https://github.com/mylukin"><img src="https://avatars.githubusercontent.com/u/1021019?v=4&s=48" width="48" height="48" alt="mylukin" title="mylukin"/></a> <a href="https://github.com/nathanbosse"><img src="https://avatars.githubusercontent.com/u/4040669?v=4&s=48" width="48" height="48" alt="nathanbosse" title="nathanbosse"/></a> <a href="https://github.com/ndraiman"><img src="https://avatars.githubusercontent.com/u/12609607?v=4&s=48" width="48" height="48" alt="ndraiman" title="ndraiman"/></a> <a href="https://github.com/nexty5870"><img src="https://avatars.githubusercontent.com/u/3869659?v=4&s=48" width="48" height="48" alt="nexty5870" title="nexty5870"/></a> <a href="https://github.com/Noctivoro"><img src="https://avatars.githubusercontent.com/u/183974570?v=4&s=48" width="48" height="48" alt="Noctivoro" title="Noctivoro"/></a> <a href="https://github.com/ozgur-polat"><img src="https://avatars.githubusercontent.com/u/26483942?v=4&s=48" width="48" height="48" alt="ozgur-polat" title="ozgur-polat"/></a>
|
||||
<a href="https://github.com/ppamment"><img src="https://avatars.githubusercontent.com/u/2122919?v=4&s=48" width="48" height="48" alt="ppamment" title="ppamment"/></a> <a href="https://github.com/prathamdby"><img src="https://avatars.githubusercontent.com/u/134331217?v=4&s=48" width="48" height="48" alt="prathamdby" title="prathamdby"/></a> <a href="https://github.com/ptn1411"><img src="https://avatars.githubusercontent.com/u/57529765?v=4&s=48" width="48" height="48" alt="ptn1411" title="ptn1411"/></a> <a href="https://github.com/reeltimeapps"><img src="https://avatars.githubusercontent.com/u/637338?v=4&s=48" width="48" height="48" alt="reeltimeapps" title="reeltimeapps"/></a> <a href="https://github.com/RLTCmpe"><img src="https://avatars.githubusercontent.com/u/10762242?v=4&s=48" width="48" height="48" alt="RLTCmpe" title="RLTCmpe"/></a> <a href="https://github.com/search?q=Rony%20Kelner"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="Rony Kelner" title="Rony Kelner"/></a> <a href="https://github.com/ryancnelson"><img src="https://avatars.githubusercontent.com/u/347171?v=4&s=48" width="48" height="48" alt="ryancnelson" title="ryancnelson"/></a> <a href="https://github.com/search?q=Samrat%20Jha"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="Samrat Jha" title="Samrat Jha"/></a> <a href="https://github.com/senoldogann"><img src="https://avatars.githubusercontent.com/u/45736551?v=4&s=48" width="48" height="48" alt="senoldogann" title="senoldogann"/></a> <a href="https://github.com/Seredeep"><img src="https://avatars.githubusercontent.com/u/22802816?v=4&s=48" width="48" height="48" alt="Seredeep" title="Seredeep"/></a>
|
||||
<a href="https://github.com/sergical"><img src="https://avatars.githubusercontent.com/u/3760543?v=4&s=48" width="48" height="48" alt="sergical" title="sergical"/></a> <a href="https://github.com/shiv19"><img src="https://avatars.githubusercontent.com/u/9407019?v=4&s=48" width="48" height="48" alt="shiv19" title="shiv19"/></a> <a href="https://github.com/shiyuanhai"><img src="https://avatars.githubusercontent.com/u/1187370?v=4&s=48" width="48" height="48" alt="shiyuanhai" title="shiyuanhai"/></a> <a href="https://github.com/siraht"><img src="https://avatars.githubusercontent.com/u/73152895?v=4&s=48" width="48" height="48" alt="siraht" title="siraht"/></a> <a href="https://github.com/snopoke"><img src="https://avatars.githubusercontent.com/u/249606?v=4&s=48" width="48" height="48" alt="snopoke" title="snopoke"/></a> <a href="https://github.com/search?q=techboss"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="techboss" title="techboss"/></a> <a href="https://github.com/testingabc321"><img src="https://avatars.githubusercontent.com/u/8577388?v=4&s=48" width="48" height="48" alt="testingabc321" title="testingabc321"/></a> <a href="https://github.com/search?q=The%20Admiral"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="The Admiral" title="The Admiral"/></a> <a href="https://github.com/thesash"><img src="https://avatars.githubusercontent.com/u/1166151?v=4&s=48" width="48" height="48" alt="thesash" title="thesash"/></a> <a href="https://github.com/search?q=Vibe%20Kanban"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="Vibe Kanban" title="Vibe Kanban"/></a>
|
||||
<a href="https://github.com/voidserf"><img src="https://avatars.githubusercontent.com/u/477673?v=4&s=48" width="48" height="48" alt="voidserf" title="voidserf"/></a> <a href="https://github.com/search?q=Vultr-Clawd%20Admin"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="Vultr-Clawd Admin" title="Vultr-Clawd Admin"/></a> <a href="https://github.com/search?q=Wimmie"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="Wimmie" title="Wimmie"/></a> <a href="https://github.com/search?q=wolfred"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="wolfred" title="wolfred"/></a> <a href="https://github.com/wstock"><img src="https://avatars.githubusercontent.com/u/1394687?v=4&s=48" width="48" height="48" alt="wstock" title="wstock"/></a> <a href="https://github.com/YangHuang2280"><img src="https://avatars.githubusercontent.com/u/201681634?v=4&s=48" width="48" height="48" alt="YangHuang2280" title="YangHuang2280"/></a> <a href="https://github.com/yazinsai"><img src="https://avatars.githubusercontent.com/u/1846034?v=4&s=48" width="48" height="48" alt="yazinsai" title="yazinsai"/></a> <a href="https://github.com/yevhen"><img src="https://avatars.githubusercontent.com/u/107726?v=4&s=48" width="48" height="48" alt="yevhen" title="yevhen"/></a> <a href="https://github.com/YiWang24"><img src="https://avatars.githubusercontent.com/u/176262341?v=4&s=48" width="48" height="48" alt="YiWang24" title="YiWang24"/></a> <a href="https://github.com/search?q=ymat19"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="ymat19" title="ymat19"/></a>
|
||||
<a href="https://github.com/search?q=Zach%20Knickerbocker"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="Zach Knickerbocker" title="Zach Knickerbocker"/></a> <a href="https://github.com/zackerthescar"><img src="https://avatars.githubusercontent.com/u/38077284?v=4&s=48" width="48" height="48" alt="zackerthescar" title="zackerthescar"/></a> <a href="https://github.com/0xJonHoldsCrypto"><img src="https://avatars.githubusercontent.com/u/81202085?v=4&s=48" width="48" height="48" alt="0xJonHoldsCrypto" title="0xJonHoldsCrypto"/></a> <a href="https://github.com/aaronn"><img src="https://avatars.githubusercontent.com/u/1653630?v=4&s=48" width="48" height="48" alt="aaronn" title="aaronn"/></a> <a href="https://github.com/Alphonse-arianee"><img src="https://avatars.githubusercontent.com/u/254457365?v=4&s=48" width="48" height="48" alt="Alphonse-arianee" title="Alphonse-arianee"/></a> <a href="https://github.com/atalovesyou"><img src="https://avatars.githubusercontent.com/u/3534502?v=4&s=48" width="48" height="48" alt="atalovesyou" title="atalovesyou"/></a> <a href="https://github.com/search?q=Azade"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="Azade" title="Azade"/></a> <a href="https://github.com/carlulsoe"><img src="https://avatars.githubusercontent.com/u/34673973?v=4&s=48" width="48" height="48" alt="carlulsoe" title="carlulsoe"/></a> <a href="https://github.com/search?q=ddyo"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="ddyo" title="ddyo"/></a> <a href="https://github.com/search?q=Erik"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="Erik" title="Erik"/></a>
|
||||
<a href="https://github.com/latitudeki5223"><img src="https://avatars.githubusercontent.com/u/119656367?v=4&s=48" width="48" height="48" alt="latitudeki5223" title="latitudeki5223"/></a> <a href="https://github.com/search?q=Manuel%20Maly"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="Manuel Maly" title="Manuel Maly"/></a> <a href="https://github.com/search?q=Mourad%20Boustani"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="Mourad Boustani" title="Mourad Boustani"/></a> <a href="https://github.com/odrobnik"><img src="https://avatars.githubusercontent.com/u/333270?v=4&s=48" width="48" height="48" alt="odrobnik" title="odrobnik"/></a> <a href="https://github.com/pcty-nextgen-ios-builder"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="pcty-nextgen-ios-builder" title="pcty-nextgen-ios-builder"/></a> <a href="https://github.com/search?q=Quentin"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="Quentin" title="Quentin"/></a> <a href="https://github.com/search?q=Randy%20Torres"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="Randy Torres" title="Randy Torres"/></a> <a href="https://github.com/rhjoh"><img src="https://avatars.githubusercontent.com/u/105699450?v=4&s=48" width="48" height="48" alt="rhjoh" title="rhjoh"/></a> <a href="https://github.com/search?q=Rolf%20Fredheim"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="Rolf Fredheim" title="Rolf Fredheim"/></a> <a href="https://github.com/ronak-guliani"><img src="https://avatars.githubusercontent.com/u/23518228?v=4&s=48" width="48" height="48" alt="ronak-guliani" title="ronak-guliani"/></a>
|
||||
<a href="https://github.com/search?q=William%20Stock"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="William Stock" title="William Stock"/></a>
|
||||
<a href="https://github.com/larlyssa"><img src="https://avatars.githubusercontent.com/u/13128869?v=4&s=48" width="48" height="48" alt="larlyssa" title="larlyssa"/></a> <a href="https://github.com/odysseus0"><img src="https://avatars.githubusercontent.com/u/8635094?v=4&s=48" width="48" height="48" alt="odysseus0" title="odysseus0"/></a> <a href="https://github.com/oswalpalash"><img src="https://avatars.githubusercontent.com/u/6431196?v=4&s=48" width="48" height="48" alt="oswalpalash" title="oswalpalash"/></a> <a href="https://github.com/pcty-nextgen-service-account"><img src="https://avatars.githubusercontent.com/u/112553441?v=4&s=48" width="48" height="48" alt="pcty-nextgen-service-account" title="pcty-nextgen-service-account"/></a> <a href="https://github.com/pi0"><img src="https://avatars.githubusercontent.com/u/5158436?v=4&s=48" width="48" height="48" alt="pi0" title="pi0"/></a> <a href="https://github.com/rmorse"><img src="https://avatars.githubusercontent.com/u/853547?v=4&s=48" width="48" height="48" alt="rmorse" title="rmorse"/></a> <a href="https://github.com/search?q=Roopak%20Nijhara"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="Roopak Nijhara" title="Roopak Nijhara"/></a> <a href="https://github.com/Syhids"><img src="https://avatars.githubusercontent.com/u/671202?v=4&s=48" width="48" height="48" alt="Syhids" title="Syhids"/></a> <a href="https://github.com/search?q=Ubuntu"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="Ubuntu" title="Ubuntu"/></a> <a href="https://github.com/search?q=xiaose"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="xiaose" title="xiaose"/></a>
|
||||
<a href="https://github.com/search?q=Aaron%20Konyer"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="Aaron Konyer" title="Aaron Konyer"/></a> <a href="https://github.com/aaronveklabs"><img src="https://avatars.githubusercontent.com/u/225997828?v=4&s=48" width="48" height="48" alt="aaronveklabs" title="aaronveklabs"/></a> <a href="https://github.com/aldoeliacim"><img src="https://avatars.githubusercontent.com/u/17973757?v=4&s=48" width="48" height="48" alt="aldoeliacim" title="aldoeliacim"/></a> <a href="https://github.com/andreabadesso"><img src="https://avatars.githubusercontent.com/u/3586068?v=4&s=48" width="48" height="48" alt="andreabadesso" title="andreabadesso"/></a> <a href="https://github.com/search?q=Andrii"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="Andrii" title="Andrii"/></a> <a href="https://github.com/BinaryMuse"><img src="https://avatars.githubusercontent.com/u/189606?v=4&s=48" width="48" height="48" alt="BinaryMuse" title="BinaryMuse"/></a> <a href="https://github.com/bqcfjwhz85-arch"><img src="https://avatars.githubusercontent.com/u/239267175?v=4&s=48" width="48" height="48" alt="bqcfjwhz85-arch" title="bqcfjwhz85-arch"/></a> <a href="https://github.com/cash-echo-bot"><img src="https://avatars.githubusercontent.com/u/252747386?v=4&s=48" width="48" height="48" alt="cash-echo-bot" title="cash-echo-bot"/></a> <a href="https://github.com/search?q=Clawd"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="Clawd" title="Clawd"/></a> <a href="https://github.com/search?q=ClawdFx"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="ClawdFx" title="ClawdFx"/></a>
|
||||
<a href="https://github.com/search?q=damaozi"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="damaozi" title="damaozi"/></a> <a href="https://github.com/danballance"><img src="https://avatars.githubusercontent.com/u/13839912?v=4&s=48" width="48" height="48" alt="danballance" title="danballance"/></a> <a href="https://github.com/Elarwei001"><img src="https://avatars.githubusercontent.com/u/168552401?v=4&s=48" width="48" height="48" alt="Elarwei001" title="Elarwei001"/></a> <a href="https://github.com/EnzeD"><img src="https://avatars.githubusercontent.com/u/9866900?v=4&s=48" width="48" height="48" alt="EnzeD" title="EnzeD"/></a> <a href="https://github.com/erik-agens"><img src="https://avatars.githubusercontent.com/u/80908960?v=4&s=48" width="48" height="48" alt="erik-agens" title="erik-agens"/></a> <a href="https://github.com/Evizero"><img src="https://avatars.githubusercontent.com/u/10854026?v=4&s=48" width="48" height="48" alt="Evizero" title="Evizero"/></a> <a href="https://github.com/fcatuhe"><img src="https://avatars.githubusercontent.com/u/17382215?v=4&s=48" width="48" height="48" alt="fcatuhe" title="fcatuhe"/></a> <a href="https://github.com/gildo"><img src="https://avatars.githubusercontent.com/u/133645?v=4&s=48" width="48" height="48" alt="gildo" title="gildo"/></a> <a href="https://github.com/hclsys"><img src="https://avatars.githubusercontent.com/u/7755017?v=4&s=48" width="48" height="48" alt="hclsys" title="hclsys"/></a> <a href="https://github.com/itsjaydesu"><img src="https://avatars.githubusercontent.com/u/220390?v=4&s=48" width="48" height="48" alt="itsjaydesu" title="itsjaydesu"/></a>
|
||||
<a href="https://github.com/ivancasco"><img src="https://avatars.githubusercontent.com/u/2452858?v=4&s=48" width="48" height="48" alt="ivancasco" title="ivancasco"/></a> <a href="https://github.com/ivanrvpereira"><img src="https://avatars.githubusercontent.com/u/183991?v=4&s=48" width="48" height="48" alt="ivanrvpereira" title="ivanrvpereira"/></a> <a href="https://github.com/search?q=Jarvis"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="Jarvis" title="Jarvis"/></a> <a href="https://github.com/jayhickey"><img src="https://avatars.githubusercontent.com/u/1676460?v=4&s=48" width="48" height="48" alt="jayhickey" title="jayhickey"/></a> <a href="https://github.com/jeffersonwarrior"><img src="https://avatars.githubusercontent.com/u/89030989?v=4&s=48" width="48" height="48" alt="jeffersonwarrior" title="jeffersonwarrior"/></a> <a href="https://github.com/search?q=jeffersonwarrior"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="jeffersonwarrior" title="jeffersonwarrior"/></a> <a href="https://github.com/jverdi"><img src="https://avatars.githubusercontent.com/u/345050?v=4&s=48" width="48" height="48" alt="jverdi" title="jverdi"/></a> <a href="https://github.com/longmaba"><img src="https://avatars.githubusercontent.com/u/9361500?v=4&s=48" width="48" height="48" alt="longmaba" title="longmaba"/></a> <a href="https://github.com/search?q=Marco%20Marandiz"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="Marco Marandiz" title="Marco Marandiz"/></a> <a href="https://github.com/MarvinCui"><img src="https://avatars.githubusercontent.com/u/130876763?v=4&s=48" width="48" height="48" alt="MarvinCui" title="MarvinCui"/></a>
|
||||
<a href="https://github.com/mjrussell"><img src="https://avatars.githubusercontent.com/u/1641895?v=4&s=48" width="48" height="48" alt="mjrussell" title="mjrussell"/></a> <a href="https://github.com/odnxe"><img src="https://avatars.githubusercontent.com/u/403141?v=4&s=48" width="48" height="48" alt="odnxe" title="odnxe"/></a> <a href="https://github.com/optimikelabs"><img src="https://avatars.githubusercontent.com/u/31423109?v=4&s=48" width="48" height="48" alt="optimikelabs" title="optimikelabs"/></a> <a href="https://github.com/p6l-richard"><img src="https://avatars.githubusercontent.com/u/18185649?v=4&s=48" width="48" height="48" alt="p6l-richard" title="p6l-richard"/></a> <a href="https://github.com/philipp-spiess"><img src="https://avatars.githubusercontent.com/u/458591?v=4&s=48" width="48" height="48" alt="philipp-spiess" title="philipp-spiess"/></a> <a href="https://github.com/search?q=Pocket%20Clawd"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="Pocket Clawd" title="Pocket Clawd"/></a> <a href="https://github.com/robaxelsen"><img src="https://avatars.githubusercontent.com/u/13132899?v=4&s=48" width="48" height="48" alt="robaxelsen" title="robaxelsen"/></a> <a href="https://github.com/search?q=Sash%20Catanzarite"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="Sash Catanzarite" title="Sash Catanzarite"/></a> <a href="https://github.com/Suksham-sharma"><img src="https://avatars.githubusercontent.com/u/94667656?v=4&s=48" width="48" height="48" alt="Suksham-sharma" title="Suksham-sharma"/></a> <a href="https://github.com/T5-AndyML"><img src="https://avatars.githubusercontent.com/u/22801233?v=4&s=48" width="48" height="48" alt="T5-AndyML" title="T5-AndyML"/></a>
|
||||
<a href="https://github.com/tewatia"><img src="https://avatars.githubusercontent.com/u/22875334?v=4&s=48" width="48" height="48" alt="tewatia" title="tewatia"/></a> <a href="https://github.com/thejhinvirtuoso"><img src="https://avatars.githubusercontent.com/u/258521837?v=4&s=48" width="48" height="48" alt="thejhinvirtuoso" title="thejhinvirtuoso"/></a> <a href="https://github.com/travisp"><img src="https://avatars.githubusercontent.com/u/165698?v=4&s=48" width="48" height="48" alt="travisp" title="travisp"/></a> <a href="https://github.com/search?q=VAC"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="VAC" title="VAC"/></a> <a href="https://github.com/search?q=william%20arzt"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="william arzt" title="william arzt"/></a> <a href="https://github.com/yudshj"><img src="https://avatars.githubusercontent.com/u/16971372?v=4&s=48" width="48" height="48" alt="yudshj" title="yudshj"/></a> <a href="https://github.com/zknicker"><img src="https://avatars.githubusercontent.com/u/1164085?v=4&s=48" width="48" height="48" alt="zknicker" title="zknicker"/></a> <a href="https://github.com/0oAstro"><img src="https://avatars.githubusercontent.com/u/79555780?v=4&s=48" width="48" height="48" alt="0oAstro" title="0oAstro"/></a> <a href="https://github.com/abhaymundhara"><img src="https://avatars.githubusercontent.com/u/62872231?v=4&s=48" width="48" height="48" alt="abhaymundhara" title="abhaymundhara"/></a> <a href="https://github.com/aduk059"><img src="https://avatars.githubusercontent.com/u/257603478?v=4&s=48" width="48" height="48" alt="aduk059" title="aduk059"/></a>
|
||||
<a href="https://github.com/akramcodez"><img src="https://avatars.githubusercontent.com/u/179671552?v=4&s=48" width="48" height="48" alt="akramcodez" title="akramcodez"/></a> <a href="https://github.com/search?q=alejandro%20maza"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="alejandro maza" title="alejandro maza"/></a> <a href="https://github.com/Alex-Alaniz"><img src="https://avatars.githubusercontent.com/u/88956822?v=4&s=48" width="48" height="48" alt="Alex-Alaniz" title="Alex-Alaniz"/></a> <a href="https://github.com/alexanderatallah"><img src="https://avatars.githubusercontent.com/u/1011391?v=4&s=48" width="48" height="48" alt="alexanderatallah" title="alexanderatallah"/></a> <a href="https://github.com/alexstyl"><img src="https://avatars.githubusercontent.com/u/1665273?v=4&s=48" width="48" height="48" alt="alexstyl" title="alexstyl"/></a> <a href="https://github.com/AlexZhangji"><img src="https://avatars.githubusercontent.com/u/3280924?v=4&s=48" width="48" height="48" alt="AlexZhangji" title="AlexZhangji"/></a> <a href="https://github.com/andrewting19"><img src="https://avatars.githubusercontent.com/u/10536704?v=4&s=48" width="48" height="48" alt="andrewting19" title="andrewting19"/></a> <a href="https://github.com/anpoirier"><img src="https://avatars.githubusercontent.com/u/1245729?v=4&s=48" width="48" height="48" alt="anpoirier" title="anpoirier"/></a> <a href="https://github.com/araa47"><img src="https://avatars.githubusercontent.com/u/22760261?v=4&s=48" width="48" height="48" alt="araa47" title="araa47"/></a> <a href="https://github.com/arthyn"><img src="https://avatars.githubusercontent.com/u/5466421?v=4&s=48" width="48" height="48" alt="arthyn" title="arthyn"/></a>
|
||||
<a href="https://github.com/Asleep123"><img src="https://avatars.githubusercontent.com/u/122379135?v=4&s=48" width="48" height="48" alt="Asleep123" title="Asleep123"/></a> <a href="https://github.com/search?q=Ayush%20Ojha"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="Ayush Ojha" title="Ayush Ojha"/></a> <a href="https://github.com/Ayush10"><img src="https://avatars.githubusercontent.com/u/7945279?v=4&s=48" width="48" height="48" alt="Ayush10" title="Ayush10"/></a> <a href="https://github.com/bguidolim"><img src="https://avatars.githubusercontent.com/u/987360?v=4&s=48" width="48" height="48" alt="bguidolim" title="bguidolim"/></a> <a href="https://github.com/bolismauro"><img src="https://avatars.githubusercontent.com/u/771999?v=4&s=48" width="48" height="48" alt="bolismauro" title="bolismauro"/></a> <a href="https://github.com/championswimmer"><img src="https://avatars.githubusercontent.com/u/1327050?v=4&s=48" width="48" height="48" alt="championswimmer" title="championswimmer"/></a> <a href="https://github.com/chenyuan99"><img src="https://avatars.githubusercontent.com/u/25518100?v=4&s=48" width="48" height="48" alt="chenyuan99" title="chenyuan99"/></a> <a href="https://github.com/Chloe-VP"><img src="https://avatars.githubusercontent.com/u/257371598?v=4&s=48" width="48" height="48" alt="Chloe-VP" title="Chloe-VP"/></a> <a href="https://github.com/search?q=Clawdbot%20Maintainers"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="Clawdbot Maintainers" title="Clawdbot Maintainers"/></a> <a href="https://github.com/conhecendoia"><img src="https://avatars.githubusercontent.com/u/82890727?v=4&s=48" width="48" height="48" alt="conhecendoia" title="conhecendoia"/></a>
|
||||
<a href="https://github.com/dasilva333"><img src="https://avatars.githubusercontent.com/u/947827?v=4&s=48" width="48" height="48" alt="dasilva333" title="dasilva333"/></a> <a href="https://github.com/David-Marsh-Photo"><img src="https://avatars.githubusercontent.com/u/228404527?v=4&s=48" width="48" height="48" alt="David-Marsh-Photo" title="David-Marsh-Photo"/></a> <a href="https://github.com/deepsoumya617"><img src="https://avatars.githubusercontent.com/u/80877391?v=4&s=48" width="48" height="48" alt="deepsoumya617" title="deepsoumya617"/></a> <a href="https://github.com/search?q=Developer"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="Developer" title="Developer"/></a> <a href="https://github.com/search?q=Dimitrios%20Ploutarchos"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="Dimitrios Ploutarchos" title="Dimitrios Ploutarchos"/></a> <a href="https://github.com/search?q=Drake%20Thomsen"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="Drake Thomsen" title="Drake Thomsen"/></a> <a href="https://github.com/dylanneve1"><img src="https://avatars.githubusercontent.com/u/31746704?v=4&s=48" width="48" height="48" alt="dylanneve1" title="dylanneve1"/></a> <a href="https://github.com/search?q=Felix%20Krause"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="Felix Krause" title="Felix Krause"/></a> <a href="https://github.com/foeken"><img src="https://avatars.githubusercontent.com/u/13864?v=4&s=48" width="48" height="48" alt="foeken" title="foeken"/></a> <a href="https://github.com/frankekn"><img src="https://avatars.githubusercontent.com/u/4488090?v=4&s=48" width="48" height="48" alt="frankekn" title="frankekn"/></a>
|
||||
<a href="https://github.com/fredheir"><img src="https://avatars.githubusercontent.com/u/3304869?v=4&s=48" width="48" height="48" alt="fredheir" title="fredheir"/></a> <a href="https://github.com/search?q=ganghyun%20kim"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="ganghyun kim" title="ganghyun kim"/></a> <a href="https://github.com/grrowl"><img src="https://avatars.githubusercontent.com/u/907140?v=4&s=48" width="48" height="48" alt="grrowl" title="grrowl"/></a> <a href="https://github.com/gtsifrikas"><img src="https://avatars.githubusercontent.com/u/8904378?v=4&s=48" width="48" height="48" alt="gtsifrikas" title="gtsifrikas"/></a> <a href="https://github.com/HassanFleyah"><img src="https://avatars.githubusercontent.com/u/228002017?v=4&s=48" width="48" height="48" alt="HassanFleyah" title="HassanFleyah"/></a> <a href="https://github.com/HazAT"><img src="https://avatars.githubusercontent.com/u/363802?v=4&s=48" width="48" height="48" alt="HazAT" title="HazAT"/></a> <a href="https://github.com/hrdwdmrbl"><img src="https://avatars.githubusercontent.com/u/554881?v=4&s=48" width="48" height="48" alt="hrdwdmrbl" title="hrdwdmrbl"/></a> <a href="https://github.com/hugobarauna"><img src="https://avatars.githubusercontent.com/u/2719?v=4&s=48" width="48" height="48" alt="hugobarauna" title="hugobarauna"/></a> <a href="https://github.com/hyf0-agent"><img src="https://avatars.githubusercontent.com/u/258783736?v=4&s=48" width="48" height="48" alt="hyf0-agent" title="hyf0-agent"/></a> <a href="https://github.com/iamEvanYT"><img src="https://avatars.githubusercontent.com/u/47493765?v=4&s=48" width="48" height="48" alt="iamEvanYT" title="iamEvanYT"/></a>
|
||||
<a href="https://github.com/ichbinlucaskim"><img src="https://avatars.githubusercontent.com/u/125564751?v=4&s=48" width="48" height="48" alt="ichbinlucaskim" title="ichbinlucaskim"/></a> <a href="https://github.com/search?q=Jamie%20Openshaw"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="Jamie Openshaw" title="Jamie Openshaw"/></a> <a href="https://github.com/search?q=Jane"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="Jane" title="Jane"/></a> <a href="https://github.com/search?q=Jarvis%20Deploy"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="Jarvis Deploy" title="Jarvis Deploy"/></a> <a href="https://github.com/search?q=Jefferson%20Nunn"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="Jefferson Nunn" title="Jefferson Nunn"/></a> <a href="https://github.com/jogi47"><img src="https://avatars.githubusercontent.com/u/1710139?v=4&s=48" width="48" height="48" alt="jogi47" title="jogi47"/></a> <a href="https://github.com/kentaro"><img src="https://avatars.githubusercontent.com/u/3458?v=4&s=48" width="48" height="48" alt="kentaro" title="kentaro"/></a> <a href="https://github.com/search?q=Kevin%20Lin"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="Kevin Lin" title="Kevin Lin"/></a> <a href="https://github.com/kira-ariaki"><img src="https://avatars.githubusercontent.com/u/257352493?v=4&s=48" width="48" height="48" alt="kira-ariaki" title="kira-ariaki"/></a> <a href="https://github.com/kitze"><img src="https://avatars.githubusercontent.com/u/1160594?v=4&s=48" width="48" height="48" alt="kitze" title="kitze"/></a>
|
||||
<a href="https://github.com/Kiwitwitter"><img src="https://avatars.githubusercontent.com/u/25277769?v=4&s=48" width="48" height="48" alt="Kiwitwitter" title="Kiwitwitter"/></a> <a href="https://github.com/lailoo"><img src="https://avatars.githubusercontent.com/u/20536249?v=4&s=48" width="48" height="48" alt="lailoo" title="lailoo"/></a> <a href="https://github.com/levifig"><img src="https://avatars.githubusercontent.com/u/1605?v=4&s=48" width="48" height="48" alt="levifig" title="levifig"/></a> <a href="https://github.com/search?q=Lloyd"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="Lloyd" title="Lloyd"/></a> <a href="https://github.com/loganaden"><img src="https://avatars.githubusercontent.com/u/1688420?v=4&s=48" width="48" height="48" alt="loganaden" title="loganaden"/></a> <a href="https://github.com/longjos"><img src="https://avatars.githubusercontent.com/u/740160?v=4&s=48" width="48" height="48" alt="longjos" title="longjos"/></a> <a href="https://github.com/loukotal"><img src="https://avatars.githubusercontent.com/u/18210858?v=4&s=48" width="48" height="48" alt="loukotal" title="loukotal"/></a> <a href="https://github.com/louzhixian"><img src="https://avatars.githubusercontent.com/u/7994361?v=4&s=48" width="48" height="48" alt="louzhixian" title="louzhixian"/></a> <a href="https://github.com/lsh411"><img src="https://avatars.githubusercontent.com/u/6801488?v=4&s=48" width="48" height="48" alt="lsh411" title="lsh411"/></a> <a href="https://github.com/M00N7682"><img src="https://avatars.githubusercontent.com/u/170746674?v=4&s=48" width="48" height="48" alt="M00N7682" title="M00N7682"/></a>
|
||||
<a href="https://github.com/search?q=mac%20mimi"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="mac mimi" title="mac mimi"/></a> <a href="https://github.com/martinpucik"><img src="https://avatars.githubusercontent.com/u/5503097?v=4&s=48" width="48" height="48" alt="martinpucik" title="martinpucik"/></a> <a href="https://github.com/search?q=Matt%20mini"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="Matt mini" title="Matt mini"/></a> <a href="https://github.com/mertcicekci0"><img src="https://avatars.githubusercontent.com/u/179321902?v=4&s=48" width="48" height="48" alt="mertcicekci0" title="mertcicekci0"/></a> <a href="https://github.com/search?q=Miles"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="Miles" title="Miles"/></a> <a href="https://github.com/mrdbstn"><img src="https://avatars.githubusercontent.com/u/58957632?v=4&s=48" width="48" height="48" alt="mrdbstn" title="mrdbstn"/></a> <a href="https://github.com/MSch"><img src="https://avatars.githubusercontent.com/u/7475?v=4&s=48" width="48" height="48" alt="MSch" title="MSch"/></a> <a href="https://github.com/mudrii"><img src="https://avatars.githubusercontent.com/u/220262?v=4&s=48" width="48" height="48" alt="mudrii" title="mudrii"/></a> <a href="https://github.com/search?q=Mustafa%20Tag%20Eldeen"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="Mustafa Tag Eldeen" title="Mustafa Tag Eldeen"/></a> <a href="https://github.com/mylukin"><img src="https://avatars.githubusercontent.com/u/1021019?v=4&s=48" width="48" height="48" alt="mylukin" title="mylukin"/></a>
|
||||
<a href="https://github.com/nathanbosse"><img src="https://avatars.githubusercontent.com/u/4040669?v=4&s=48" width="48" height="48" alt="nathanbosse" title="nathanbosse"/></a> <a href="https://github.com/ndraiman"><img src="https://avatars.githubusercontent.com/u/12609607?v=4&s=48" width="48" height="48" alt="ndraiman" title="ndraiman"/></a> <a href="https://github.com/nexty5870"><img src="https://avatars.githubusercontent.com/u/3869659?v=4&s=48" width="48" height="48" alt="nexty5870" title="nexty5870"/></a> <a href="https://github.com/Noctivoro"><img src="https://avatars.githubusercontent.com/u/183974570?v=4&s=48" width="48" height="48" alt="Noctivoro" title="Noctivoro"/></a> <a href="https://github.com/ozgur-polat"><img src="https://avatars.githubusercontent.com/u/26483942?v=4&s=48" width="48" height="48" alt="ozgur-polat" title="ozgur-polat"/></a> <a href="https://github.com/ppamment"><img src="https://avatars.githubusercontent.com/u/2122919?v=4&s=48" width="48" height="48" alt="ppamment" title="ppamment"/></a> <a href="https://github.com/prathamdby"><img src="https://avatars.githubusercontent.com/u/134331217?v=4&s=48" width="48" height="48" alt="prathamdby" title="prathamdby"/></a> <a href="https://github.com/ptn1411"><img src="https://avatars.githubusercontent.com/u/57529765?v=4&s=48" width="48" height="48" alt="ptn1411" title="ptn1411"/></a> <a href="https://github.com/reeltimeapps"><img src="https://avatars.githubusercontent.com/u/637338?v=4&s=48" width="48" height="48" alt="reeltimeapps" title="reeltimeapps"/></a> <a href="https://github.com/RLTCmpe"><img src="https://avatars.githubusercontent.com/u/10762242?v=4&s=48" width="48" height="48" alt="RLTCmpe" title="RLTCmpe"/></a>
|
||||
<a href="https://github.com/search?q=Rony%20Kelner"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="Rony Kelner" title="Rony Kelner"/></a> <a href="https://github.com/ryancnelson"><img src="https://avatars.githubusercontent.com/u/347171?v=4&s=48" width="48" height="48" alt="ryancnelson" title="ryancnelson"/></a> <a href="https://github.com/search?q=Samrat%20Jha"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="Samrat Jha" title="Samrat Jha"/></a> <a href="https://github.com/senoldogann"><img src="https://avatars.githubusercontent.com/u/45736551?v=4&s=48" width="48" height="48" alt="senoldogann" title="senoldogann"/></a> <a href="https://github.com/Seredeep"><img src="https://avatars.githubusercontent.com/u/22802816?v=4&s=48" width="48" height="48" alt="Seredeep" title="Seredeep"/></a> <a href="https://github.com/sergical"><img src="https://avatars.githubusercontent.com/u/3760543?v=4&s=48" width="48" height="48" alt="sergical" title="sergical"/></a> <a href="https://github.com/shiv19"><img src="https://avatars.githubusercontent.com/u/9407019?v=4&s=48" width="48" height="48" alt="shiv19" title="shiv19"/></a> <a href="https://github.com/shiyuanhai"><img src="https://avatars.githubusercontent.com/u/1187370?v=4&s=48" width="48" height="48" alt="shiyuanhai" title="shiyuanhai"/></a> <a href="https://github.com/siraht"><img src="https://avatars.githubusercontent.com/u/73152895?v=4&s=48" width="48" height="48" alt="siraht" title="siraht"/></a> <a href="https://github.com/snopoke"><img src="https://avatars.githubusercontent.com/u/249606?v=4&s=48" width="48" height="48" alt="snopoke" title="snopoke"/></a>
|
||||
<a href="https://github.com/stephenchen2025"><img src="https://avatars.githubusercontent.com/u/218387130?v=4&s=48" width="48" height="48" alt="stephenchen2025" title="stephenchen2025"/></a> <a href="https://github.com/search?q=techboss"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="techboss" title="techboss"/></a> <a href="https://github.com/testingabc321"><img src="https://avatars.githubusercontent.com/u/8577388?v=4&s=48" width="48" height="48" alt="testingabc321" title="testingabc321"/></a> <a href="https://github.com/search?q=The%20Admiral"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="The Admiral" title="The Admiral"/></a> <a href="https://github.com/thesash"><img src="https://avatars.githubusercontent.com/u/1166151?v=4&s=48" width="48" height="48" alt="thesash" title="thesash"/></a> <a href="https://github.com/search?q=Vibe%20Kanban"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="Vibe Kanban" title="Vibe Kanban"/></a> <a href="https://github.com/voidserf"><img src="https://avatars.githubusercontent.com/u/477673?v=4&s=48" width="48" height="48" alt="voidserf" title="voidserf"/></a> <a href="https://github.com/search?q=Vultr-Clawd%20Admin"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="Vultr-Clawd Admin" title="Vultr-Clawd Admin"/></a> <a href="https://github.com/search?q=Wimmie"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="Wimmie" title="Wimmie"/></a> <a href="https://github.com/search?q=wolfred"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="wolfred" title="wolfred"/></a>
|
||||
<a href="https://github.com/wstock"><img src="https://avatars.githubusercontent.com/u/1394687?v=4&s=48" width="48" height="48" alt="wstock" title="wstock"/></a> <a href="https://github.com/wytheme"><img src="https://avatars.githubusercontent.com/u/5009358?v=4&s=48" width="48" height="48" alt="wytheme" title="wytheme"/></a> <a href="https://github.com/YangHuang2280"><img src="https://avatars.githubusercontent.com/u/201681634?v=4&s=48" width="48" height="48" alt="YangHuang2280" title="YangHuang2280"/></a> <a href="https://github.com/yazinsai"><img src="https://avatars.githubusercontent.com/u/1846034?v=4&s=48" width="48" height="48" alt="yazinsai" title="yazinsai"/></a> <a href="https://github.com/yevhen"><img src="https://avatars.githubusercontent.com/u/107726?v=4&s=48" width="48" height="48" alt="yevhen" title="yevhen"/></a> <a href="https://github.com/YiWang24"><img src="https://avatars.githubusercontent.com/u/176262341?v=4&s=48" width="48" height="48" alt="YiWang24" title="YiWang24"/></a> <a href="https://github.com/search?q=ymat19"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="ymat19" title="ymat19"/></a> <a href="https://github.com/search?q=Zach%20Knickerbocker"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="Zach Knickerbocker" title="Zach Knickerbocker"/></a> <a href="https://github.com/zackerthescar"><img src="https://avatars.githubusercontent.com/u/38077284?v=4&s=48" width="48" height="48" alt="zackerthescar" title="zackerthescar"/></a> <a href="https://github.com/0xJonHoldsCrypto"><img src="https://avatars.githubusercontent.com/u/81202085?v=4&s=48" width="48" height="48" alt="0xJonHoldsCrypto" title="0xJonHoldsCrypto"/></a>
|
||||
<a href="https://github.com/aaronn"><img src="https://avatars.githubusercontent.com/u/1653630?v=4&s=48" width="48" height="48" alt="aaronn" title="aaronn"/></a> <a href="https://github.com/Alphonse-arianee"><img src="https://avatars.githubusercontent.com/u/254457365?v=4&s=48" width="48" height="48" alt="Alphonse-arianee" title="Alphonse-arianee"/></a> <a href="https://github.com/atalovesyou"><img src="https://avatars.githubusercontent.com/u/3534502?v=4&s=48" width="48" height="48" alt="atalovesyou" title="atalovesyou"/></a> <a href="https://github.com/search?q=Azade"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="Azade" title="Azade"/></a> <a href="https://github.com/carlulsoe"><img src="https://avatars.githubusercontent.com/u/34673973?v=4&s=48" width="48" height="48" alt="carlulsoe" title="carlulsoe"/></a> <a href="https://github.com/search?q=ddyo"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="ddyo" title="ddyo"/></a> <a href="https://github.com/search?q=Erik"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="Erik" title="Erik"/></a> <a href="https://github.com/jiulingyun"><img src="https://avatars.githubusercontent.com/u/126459548?v=4&s=48" width="48" height="48" alt="jiulingyun" title="jiulingyun"/></a> <a href="https://github.com/latitudeki5223"><img src="https://avatars.githubusercontent.com/u/119656367?v=4&s=48" width="48" height="48" alt="latitudeki5223" title="latitudeki5223"/></a> <a href="https://github.com/search?q=Manuel%20Maly"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="Manuel Maly" title="Manuel Maly"/></a>
|
||||
<a href="https://github.com/search?q=Mourad%20Boustani"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="Mourad Boustani" title="Mourad Boustani"/></a> <a href="https://github.com/odrobnik"><img src="https://avatars.githubusercontent.com/u/333270?v=4&s=48" width="48" height="48" alt="odrobnik" title="odrobnik"/></a> <a href="https://github.com/pcty-nextgen-ios-builder"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="pcty-nextgen-ios-builder" title="pcty-nextgen-ios-builder"/></a> <a href="https://github.com/search?q=Quentin"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="Quentin" title="Quentin"/></a> <a href="https://github.com/search?q=Randy%20Torres"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="Randy Torres" title="Randy Torres"/></a> <a href="https://github.com/rhjoh"><img src="https://avatars.githubusercontent.com/u/105699450?v=4&s=48" width="48" height="48" alt="rhjoh" title="rhjoh"/></a> <a href="https://github.com/search?q=Rolf%20Fredheim"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="Rolf Fredheim" title="Rolf Fredheim"/></a> <a href="https://github.com/ronak-guliani"><img src="https://avatars.githubusercontent.com/u/23518228?v=4&s=48" width="48" height="48" alt="ronak-guliani" title="ronak-guliani"/></a> <a href="https://github.com/search?q=William%20Stock"><img src="assets/avatar-placeholder.svg" width="48" height="48" alt="William Stock" title="William Stock"/></a>
|
||||
</p>
|
||||
|
||||
97
appcast.xml
97
appcast.xml
@@ -2,6 +2,56 @@
|
||||
<rss xmlns:sparkle="http://www.andymatuschak.org/xml-namespaces/sparkle" version="2.0">
|
||||
<channel>
|
||||
<title>OpenClaw</title>
|
||||
<item>
|
||||
<title>2026.2.3</title>
|
||||
<pubDate>Wed, 04 Feb 2026 17:47:10 -0800</pubDate>
|
||||
<link>https://raw.githubusercontent.com/openclaw/openclaw/main/appcast.xml</link>
|
||||
<sparkle:version>8900</sparkle:version>
|
||||
<sparkle:shortVersionString>2026.2.3</sparkle:shortVersionString>
|
||||
<sparkle:minimumSystemVersion>15.0</sparkle:minimumSystemVersion>
|
||||
<description><![CDATA[<h2>OpenClaw 2026.2.3</h2>
|
||||
<h3>Changes</h3>
|
||||
<ul>
|
||||
<li>Telegram: remove last <code>@ts-nocheck</code> from <code>bot-handlers.ts</code>, use Grammy types directly, deduplicate <code>StickerMetadata</code>. Zero <code>@ts-nocheck</code> remaining in <code>src/telegram/</code>. (#9206)</li>
|
||||
<li>Telegram: remove <code>@ts-nocheck</code> from <code>bot-message.ts</code>, type deps via <code>Omit<BuildTelegramMessageContextParams></code>, widen <code>allMedia</code> to <code>TelegramMediaRef[]</code>. (#9180)</li>
|
||||
<li>Telegram: remove <code>@ts-nocheck</code> from <code>bot.ts</code>, fix duplicate <code>bot.catch</code> error handler (Grammy overrides), remove dead reaction <code>message_thread_id</code> routing, harden sticker cache guard. (#9077)</li>
|
||||
<li>Onboarding: add Cloudflare AI Gateway provider setup and docs. (#7914) Thanks @roerohan.</li>
|
||||
<li>Onboarding: add Moonshot (.cn) auth choice and keep the China base URL when preserving defaults. (#7180) Thanks @waynelwz.</li>
|
||||
<li>Docs: clarify tmux send-keys for TUI by splitting text and Enter. (#7737) Thanks @Wangnov.</li>
|
||||
<li>Docs: mirror the landing page revamp for zh-CN (features, quickstart, docs directory, network model, credits). (#8994) Thanks @joshp123.</li>
|
||||
<li>Messages: add per-channel and per-account responsePrefix overrides across channels. (#9001) Thanks @mudrii.</li>
|
||||
<li>Cron: add announce delivery mode for isolated jobs (CLI + Control UI) and delivery mode config.</li>
|
||||
<li>Cron: default isolated jobs to announce delivery; accept ISO 8601 <code>schedule.at</code> in tool inputs.</li>
|
||||
<li>Cron: hard-migrate isolated jobs to announce/none delivery; drop legacy post-to-main/payload delivery fields and <code>atMs</code> inputs.</li>
|
||||
<li>Cron: delete one-shot jobs after success by default; add <code>--keep-after-run</code> for CLI.</li>
|
||||
<li>Cron: suppress messaging tools during announce delivery so summaries post consistently.</li>
|
||||
<li>Cron: avoid duplicate deliveries when isolated runs send messages directly.</li>
|
||||
</ul>
|
||||
<h3>Fixes</h3>
|
||||
<ul>
|
||||
<li>Heartbeat: allow explicit accountId routing for multi-account channels. (#8702) Thanks @lsh411.</li>
|
||||
<li>TUI/Gateway: handle non-streaming finals, refresh history for non-local chat runs, and avoid event gap warnings for targeted tool streams. (#8432) Thanks @gumadeiras.</li>
|
||||
<li>Shell completion: auto-detect and migrate slow dynamic patterns to cached files for faster terminal startup; add completion health checks to doctor/update/onboard.</li>
|
||||
<li>Telegram: honor session model overrides in inline model selection. (#8193) Thanks @gildo.</li>
|
||||
<li>Web UI: fix agent model selection saves for default/non-default agents and wrap long workspace paths. Thanks @Takhoffman.</li>
|
||||
<li>Web UI: resolve header logo path when <code>gateway.controlUi.basePath</code> is set. (#7178) Thanks @Yeom-JinHo.</li>
|
||||
<li>Web UI: apply button styling to the new-messages indicator.</li>
|
||||
<li>Security: keep untrusted channel metadata out of system prompts (Slack/Discord). Thanks @KonstantinMirin.</li>
|
||||
<li>Security: enforce sandboxed media paths for message tool attachments. (#9182) Thanks @victormier.</li>
|
||||
<li>Security: require explicit credentials for gateway URL overrides to prevent credential leakage. (#8113) Thanks @victormier.</li>
|
||||
<li>Security: gate <code>whatsapp_login</code> tool to owner senders and default-deny non-owner contexts. (#8768) Thanks @victormier.</li>
|
||||
<li>Voice call: harden webhook verification with host allowlists/proxy trust and keep ngrok loopback bypass.</li>
|
||||
<li>Voice call: add regression coverage for anonymous inbound caller IDs with allowlist policy. (#8104) Thanks @victormier.</li>
|
||||
<li>Cron: accept epoch timestamps and 0ms durations in CLI <code>--at</code> parsing.</li>
|
||||
<li>Cron: reload store data when the store file is recreated or mtime changes.</li>
|
||||
<li>Cron: deliver announce runs directly, honor delivery mode, and respect wakeMode for summaries. (#8540) Thanks @tyler6204.</li>
|
||||
<li>Telegram: include forward_from_chat metadata in forwarded messages and harden cron delivery target checks. (#8392) Thanks @Glucksberg.</li>
|
||||
<li>macOS: fix cron payload summary rendering and ISO 8601 formatter concurrency safety.</li>
|
||||
</ul>
|
||||
<p><a href="https://github.com/openclaw/openclaw/blob/main/CHANGELOG.md">View full changelog</a></p>
|
||||
]]></description>
|
||||
<enclosure url="https://github.com/openclaw/openclaw/releases/download/v2026.2.3/OpenClaw-2026.2.3.zip" length="22530161" type="application/octet-stream" sparkle:edSignature="7eHUaQC6cx87HWbcaPh9T437+LqfE9VtQBf4p9JBjIyBrqGYxxp9KPvI5unEjg55j9j2djCXhseSMeyyRmvYBg=="/>
|
||||
</item>
|
||||
<item>
|
||||
<title>2026.2.2</title>
|
||||
<pubDate>Tue, 03 Feb 2026 17:04:17 -0800</pubDate>
|
||||
@@ -112,50 +162,5 @@
|
||||
]]></description>
|
||||
<enclosure url="https://github.com/openclaw/openclaw/releases/download/v2026.2.1/OpenClaw-2026.2.1.zip" length="22458919" type="application/octet-stream" sparkle:edSignature="kA/8VQlVdtYphcB1iuFrhWczwWKgkVZMfDfQ7T9WD405D8JKTv5CZ1n8lstIVkpk4xog3UhrfaaoTG8Bf8DMAQ=="/>
|
||||
</item>
|
||||
<item>
|
||||
<title>2026.1.30</title>
|
||||
<pubDate>Sat, 31 Jan 2026 14:29:57 +0100</pubDate>
|
||||
<link>https://raw.githubusercontent.com/openclaw/openclaw/main/appcast.xml</link>
|
||||
<sparkle:version>8469</sparkle:version>
|
||||
<sparkle:shortVersionString>2026.1.30</sparkle:shortVersionString>
|
||||
<sparkle:minimumSystemVersion>15.0</sparkle:minimumSystemVersion>
|
||||
<description><![CDATA[<h2>OpenClaw 2026.1.30</h2>
|
||||
<h3>Changes</h3>
|
||||
<ul>
|
||||
<li>CLI: add <code>completion</code> command (Zsh/Bash/PowerShell/Fish) and auto-setup during postinstall/onboarding.</li>
|
||||
<li>CLI: add per-agent <code>models status</code> (<code>--agent</code> filter). (#4780) Thanks @jlowin.</li>
|
||||
<li>Agents: add Kimi K2.5 to the synthetic model catalog. (#4407) Thanks @manikv12.</li>
|
||||
<li>Auth: switch Kimi Coding to built-in provider; normalize OAuth profile email.</li>
|
||||
<li>Auth: add MiniMax OAuth plugin + onboarding option. (#4521) Thanks @Maosghoul.</li>
|
||||
<li>Agents: update pi SDK/API usage and dependencies.</li>
|
||||
<li>Web UI: refresh sessions after chat commands and improve session display names.</li>
|
||||
<li>Build: move TypeScript builds to <code>tsdown</code> + <code>tsgo</code> (faster builds, CI typechecks), update tsconfig target, and clean up lint rules.</li>
|
||||
<li>Build: align npm tar override and bin metadata so the <code>openclaw</code> CLI entrypoint is preserved in npm publishes.</li>
|
||||
<li>Docs: add pi/pi-dev docs and update OpenClaw branding + install links.</li>
|
||||
</ul>
|
||||
<h3>Fixes</h3>
|
||||
<ul>
|
||||
<li>Security: restrict local path extraction in media parser to prevent LFI. (#4880)</li>
|
||||
<li>Gateway: prevent token defaults from becoming the literal "undefined". (#4873) Thanks @Hisleren.</li>
|
||||
<li>Control UI: fix assets resolution for npm global installs. (#4909) Thanks @YuriNachos.</li>
|
||||
<li>macOS: avoid stderr pipe backpressure in gateway discovery. (#3304) Thanks @abhijeet117.</li>
|
||||
<li>Telegram: normalize account token lookup for non-normalized IDs. (#5055) Thanks @jasonsschin.</li>
|
||||
<li>Telegram: preserve delivery thread fallback and fix threadId handling in delivery context.</li>
|
||||
<li>Telegram: fix HTML nesting for overlapping styles/links. (#4578) Thanks @ThanhNguyxn.</li>
|
||||
<li>Telegram: accept numeric messageId/chatId in react actions. (#4533) Thanks @Ayush10.</li>
|
||||
<li>Telegram: honor per-account proxy dispatcher via undici fetch. (#4456) Thanks @spiceoogway.</li>
|
||||
<li>Telegram: scope skill commands to bound agent per bot. (#4360) Thanks @robhparker.</li>
|
||||
<li>BlueBubbles: debounce by messageId to preserve attachments in text+image messages. (#4984)</li>
|
||||
<li>Routing: prefer requesterOrigin over stale session entries for sub-agent announce delivery. (#4957)</li>
|
||||
<li>Extensions: restore embedded extension discovery typings.</li>
|
||||
<li>CLI: fix <code>tui:dev</code> port resolution.</li>
|
||||
<li>LINE: fix status command TypeError. (#4651)</li>
|
||||
<li>OAuth: skip expired-token warnings when refresh tokens are still valid. (#4593)</li>
|
||||
<li>Build: skip redundant UI install step in Dockerfile. (#4584) Thanks @obviyus.</li>
|
||||
</ul>
|
||||
<p><a href="https://github.com/openclaw/openclaw/blob/main/CHANGELOG.md">View full changelog</a></p>
|
||||
]]></description>
|
||||
<enclosure url="https://github.com/openclaw/openclaw/releases/download/v2026.1.30/OpenClaw-2026.1.30.zip" length="22458594" type="application/octet-stream" sparkle:edSignature="77/GuEcruKGgu2CJyMq+OVwzaJ2v1VzRQC9NmOirKO3uH5Nn5HaoouwrOHnOanrzlD4OvPW0FS5GH2E4Ntu4CQ=="/>
|
||||
</item>
|
||||
</channel>
|
||||
</rss>
|
||||
</rss>
|
||||
|
||||
@@ -22,7 +22,7 @@ android {
|
||||
minSdk = 31
|
||||
targetSdk = 36
|
||||
versionCode = 202602030
|
||||
versionName = "2026.2.3"
|
||||
versionName = "2026.2.4"
|
||||
}
|
||||
|
||||
buildTypes {
|
||||
|
||||
@@ -19,7 +19,7 @@
|
||||
<key>CFBundlePackageType</key>
|
||||
<string>APPL</string>
|
||||
<key>CFBundleShortVersionString</key>
|
||||
<string>2026.2.3</string>
|
||||
<string>2026.2.4</string>
|
||||
<key>CFBundleVersion</key>
|
||||
<string>20260202</string>
|
||||
<key>NSAppTransportSecurity</key>
|
||||
|
||||
@@ -17,7 +17,7 @@
|
||||
<key>CFBundlePackageType</key>
|
||||
<string>BNDL</string>
|
||||
<key>CFBundleShortVersionString</key>
|
||||
<string>2026.2.3</string>
|
||||
<string>2026.2.4</string>
|
||||
<key>CFBundleVersion</key>
|
||||
<string>20260202</string>
|
||||
</dict>
|
||||
|
||||
@@ -81,7 +81,7 @@ targets:
|
||||
properties:
|
||||
CFBundleDisplayName: OpenClaw
|
||||
CFBundleIconName: AppIcon
|
||||
CFBundleShortVersionString: "2026.2.3"
|
||||
CFBundleShortVersionString: "2026.2.4"
|
||||
CFBundleVersion: "20260202"
|
||||
UILaunchScreen: {}
|
||||
UIApplicationSceneManifest:
|
||||
@@ -130,5 +130,5 @@ targets:
|
||||
path: Tests/Info.plist
|
||||
properties:
|
||||
CFBundleDisplayName: OpenClawTests
|
||||
CFBundleShortVersionString: "2026.2.3"
|
||||
CFBundleShortVersionString: "2026.2.4"
|
||||
CFBundleVersion: "20260202"
|
||||
|
||||
@@ -97,25 +97,21 @@ enum CronSchedule: Codable, Equatable {
|
||||
static func parseAtDate(_ value: String) -> Date? {
|
||||
let trimmed = value.trimmingCharacters(in: .whitespacesAndNewlines)
|
||||
if trimmed.isEmpty { return nil }
|
||||
if let date = isoFormatterWithFractional.date(from: trimmed) { return date }
|
||||
return isoFormatter.date(from: trimmed)
|
||||
if let date = makeIsoFormatter(withFractional: true).date(from: trimmed) { return date }
|
||||
return makeIsoFormatter(withFractional: false).date(from: trimmed)
|
||||
}
|
||||
|
||||
static func formatIsoDate(_ date: Date) -> String {
|
||||
isoFormatter.string(from: date)
|
||||
makeIsoFormatter(withFractional: false).string(from: date)
|
||||
}
|
||||
|
||||
private static let isoFormatter: ISO8601DateFormatter = {
|
||||
private static func makeIsoFormatter(withFractional: Bool) -> ISO8601DateFormatter {
|
||||
let formatter = ISO8601DateFormatter()
|
||||
formatter.formatOptions = [.withInternetDateTime]
|
||||
formatter.formatOptions = withFractional
|
||||
? [.withInternetDateTime, .withFractionalSeconds]
|
||||
: [.withInternetDateTime]
|
||||
return formatter
|
||||
}()
|
||||
|
||||
private static let isoFormatterWithFractional: ISO8601DateFormatter = {
|
||||
let formatter = ISO8601DateFormatter()
|
||||
formatter.formatOptions = [.withInternetDateTime, .withFractionalSeconds]
|
||||
return formatter
|
||||
}()
|
||||
}
|
||||
}
|
||||
|
||||
enum CronPayload: Codable, Equatable {
|
||||
|
||||
@@ -207,7 +207,7 @@ extension CronSettings {
|
||||
|
||||
func payloadSummary(_ job: CronJob) -> some View {
|
||||
let payload = job.payload
|
||||
VStack(alignment: .leading, spacing: 6) {
|
||||
return VStack(alignment: .leading, spacing: 6) {
|
||||
Text("Payload")
|
||||
.font(.caption.weight(.semibold))
|
||||
.foregroundStyle(.secondary)
|
||||
|
||||
@@ -335,7 +335,7 @@ extension OnboardingView {
|
||||
.multilineTextAlignment(.center)
|
||||
.frame(maxWidth: 540)
|
||||
.fixedSize(horizontal: false, vertical: true)
|
||||
Text("OpenClaw supports any model — we strongly recommend Opus 4.5 for the best experience.")
|
||||
Text("OpenClaw supports any model — we strongly recommend Opus 4.6 for the best experience.")
|
||||
.font(.callout)
|
||||
.foregroundStyle(.secondary)
|
||||
.multilineTextAlignment(.center)
|
||||
|
||||
@@ -15,7 +15,7 @@
|
||||
<key>CFBundlePackageType</key>
|
||||
<string>APPL</string>
|
||||
<key>CFBundleShortVersionString</key>
|
||||
<string>2026.2.3</string>
|
||||
<string>2026.2.4</string>
|
||||
<key>CFBundleVersion</key>
|
||||
<string>202602020</string>
|
||||
<key>CFBundleIconFile</key>
|
||||
|
||||
@@ -169,7 +169,7 @@ extension SessionRow {
|
||||
systemSent: true,
|
||||
abortedLastRun: true,
|
||||
tokens: SessionTokenStats(input: 5000, output: 1200, total: 6200, contextTokens: 200_000),
|
||||
model: "claude-opus-4-5"),
|
||||
model: "claude-opus-4-6"),
|
||||
SessionRow(
|
||||
id: "global",
|
||||
key: "global",
|
||||
@@ -242,7 +242,7 @@ struct SessionStoreSnapshot {
|
||||
|
||||
@MainActor
|
||||
enum SessionLoader {
|
||||
static let fallbackModel = "claude-opus-4-5"
|
||||
static let fallbackModel = "claude-opus-4-6"
|
||||
static let fallbackContextTokens = 200_000
|
||||
|
||||
static let defaultStorePath = standardize(
|
||||
|
||||
@@ -23,7 +23,7 @@ struct MenuSessionsInjectorTests {
|
||||
let injector = MenuSessionsInjector()
|
||||
injector.setTestingControlChannelConnected(true)
|
||||
|
||||
let defaults = SessionDefaults(model: "anthropic/claude-opus-4-5", contextTokens: 200_000)
|
||||
let defaults = SessionDefaults(model: "anthropic/claude-opus-4-6", contextTokens: 200_000)
|
||||
let rows = [
|
||||
SessionRow(
|
||||
id: "main",
|
||||
@@ -41,7 +41,7 @@ struct MenuSessionsInjectorTests {
|
||||
systemSent: false,
|
||||
abortedLastRun: false,
|
||||
tokens: SessionTokenStats(input: 10, output: 20, total: 30, contextTokens: 200_000),
|
||||
model: "claude-opus-4-5"),
|
||||
model: "claude-opus-4-6"),
|
||||
SessionRow(
|
||||
id: "discord:group:alpha",
|
||||
key: "discord:group:alpha",
|
||||
@@ -58,7 +58,7 @@ struct MenuSessionsInjectorTests {
|
||||
systemSent: true,
|
||||
abortedLastRun: true,
|
||||
tokens: SessionTokenStats(input: 50, output: 50, total: 100, contextTokens: 200_000),
|
||||
model: "claude-opus-4-5"),
|
||||
model: "claude-opus-4-6"),
|
||||
]
|
||||
let snapshot = SessionStoreSnapshot(
|
||||
storePath: "/tmp/sessions.json",
|
||||
|
||||
@@ -39,6 +39,26 @@
|
||||
"source": "Getting started",
|
||||
"target": "入门指南"
|
||||
},
|
||||
{
|
||||
"source": "Quick start",
|
||||
"target": "快速开始"
|
||||
},
|
||||
{
|
||||
"source": "Quick Start",
|
||||
"target": "快速开始"
|
||||
},
|
||||
{
|
||||
"source": "Docs directory",
|
||||
"target": "文档目录"
|
||||
},
|
||||
{
|
||||
"source": "Credits",
|
||||
"target": "致谢"
|
||||
},
|
||||
{
|
||||
"source": "Features",
|
||||
"target": "功能"
|
||||
},
|
||||
{
|
||||
"source": "DMs",
|
||||
"target": "私信"
|
||||
|
||||
@@ -1,53 +0,0 @@
|
||||
title: "OpenClaw Docs"
|
||||
description: "A TypeScript/Node gateway + macOS/iOS/Android companions for WhatsApp (web) and Telegram (bot)."
|
||||
markdown: kramdown
|
||||
highlighter: rouge
|
||||
|
||||
# Keep GitHub Pages' default page URLs (e.g. /gateway.html). Many docs links
|
||||
# are written as relative *.md links and are rewritten during the build.
|
||||
|
||||
plugins:
|
||||
- jekyll-relative-links
|
||||
|
||||
relative_links:
|
||||
enabled: true
|
||||
collections: true
|
||||
|
||||
defaults:
|
||||
- scope:
|
||||
path: ""
|
||||
values:
|
||||
layout: default
|
||||
|
||||
nav:
|
||||
- title: "Home"
|
||||
url: "/"
|
||||
- title: "OpenClaw Assistant"
|
||||
url: "/start/openclaw/"
|
||||
- title: "Gateway"
|
||||
url: "/gateway/"
|
||||
- title: "Remote"
|
||||
url: "/gateway/remote/"
|
||||
- title: "Discovery"
|
||||
url: "/gateway/discovery/"
|
||||
- title: "Configuration"
|
||||
url: "/gateway/configuration/"
|
||||
- title: "WebChat"
|
||||
url: "/web/webchat/"
|
||||
- title: "macOS App"
|
||||
url: "/platforms/macos/"
|
||||
- title: "iOS App"
|
||||
url: "/platforms/ios/"
|
||||
- title: "Android App"
|
||||
url: "/platforms/android/"
|
||||
- title: "Telegram"
|
||||
url: "/channels/telegram/"
|
||||
- title: "Security"
|
||||
url: "/gateway/security/"
|
||||
- title: "Troubleshooting"
|
||||
url: "/gateway/troubleshooting/"
|
||||
|
||||
kramdown:
|
||||
input: GFM
|
||||
hard_wrap: false
|
||||
syntax_highlighter: rouge
|
||||
@@ -1,145 +0,0 @@
|
||||
<!doctype html>
|
||||
<html lang="en" data-theme="auto">
|
||||
<head>
|
||||
<meta charset="utf-8" />
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1" />
|
||||
<meta name="color-scheme" content="light dark" />
|
||||
<title>
|
||||
{% if page.url == "/" %}{{ site.title }}{% else %}{{ page.title | default: page.path | split: "/" | last | replace: ".md", "" }} · {{ site.title }}{% endif %}
|
||||
</title>
|
||||
|
||||
<link rel="preconnect" href="https://fonts.googleapis.com" />
|
||||
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin />
|
||||
<link
|
||||
href="https://fonts.googleapis.com/css2?family=Pixelify+Sans:wght@400..700&family=Fragment+Mono:ital,wght@0,400;0,700;1,400;1,700&display=swap"
|
||||
rel="stylesheet"
|
||||
/>
|
||||
<script>
|
||||
(() => {
|
||||
try {
|
||||
const stored = localStorage.getItem("openclaw:theme");
|
||||
if (stored === "light" || stored === "dark") document.documentElement.dataset.theme = stored;
|
||||
} catch {
|
||||
// ignore
|
||||
}
|
||||
})();
|
||||
</script>
|
||||
<link rel="stylesheet" href="{{ "/assets/terminal.css" | relative_url }}" />
|
||||
<link rel="stylesheet" href="{{ "/assets/markdown.css" | relative_url }}" />
|
||||
<script defer src="{{ "/assets/theme.js" | relative_url }}"></script>
|
||||
</head>
|
||||
|
||||
<body>
|
||||
<a class="skip-link" href="#content">Skip to content</a>
|
||||
|
||||
<header class="shell">
|
||||
<div class="shell__frame" role="banner">
|
||||
<div class="shell__titlebar">
|
||||
<div class="brand" aria-label="OpenClaw docs terminal">
|
||||
<img
|
||||
class="brand__logo"
|
||||
src="{{ "/assets/pixel-lobster.svg" | relative_url }}"
|
||||
alt=""
|
||||
width="40"
|
||||
height="40"
|
||||
decoding="async"
|
||||
/>
|
||||
<div class="brand__text">
|
||||
<div class="brand__name">OpenClaw</div>
|
||||
<div class="brand__hint">docs // lobster terminal</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div class="titlebar__actions">
|
||||
<a class="titlebar__cta" href="https://github.com/openclaw/openclaw">
|
||||
<span class="titlebar__cta-label">GitHub</span>
|
||||
<span class="titlebar__cta-meta">repo</span>
|
||||
</a>
|
||||
<a class="titlebar__cta titlebar__cta--accent" href="https://github.com/openclaw/openclaw/releases/latest">
|
||||
<span class="titlebar__cta-label">Download</span>
|
||||
<span class="titlebar__cta-meta">latest</span>
|
||||
</a>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div class="shell__nav" aria-label="Primary">
|
||||
<nav class="nav">
|
||||
{% assign nav = site.nav | default: empty %}
|
||||
{% for item in nav %}
|
||||
{% assign item_url = item.url | relative_url %}
|
||||
<a class="nav__link" href="{{ item_url }}">
|
||||
<span class="nav__chev">›</span>{{ item.title }}
|
||||
</a>
|
||||
{% endfor %}
|
||||
</nav>
|
||||
|
||||
<div class="shell__status" aria-hidden="true">
|
||||
<span class="status__dot"></span>
|
||||
<span class="status__text">
|
||||
{% if page.url == "/" %}
|
||||
ready
|
||||
{% else %}
|
||||
viewing: {{ page.path }}
|
||||
{% endif %}
|
||||
</span>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</header>
|
||||
|
||||
<main id="content" class="content" role="main">
|
||||
<div class="terminal">
|
||||
<div class="terminal__prompt" aria-hidden="true">
|
||||
<span class="prompt__user">openclaw</span>@<span class="prompt__host">openclaw</span>:<span class="prompt__path">~/docs</span>$<span class="prompt__cmd">
|
||||
{% if page.url == "/" %}cat index.md{% else %}less {{ page.path }}{% endif %}
|
||||
</span>
|
||||
</div>
|
||||
|
||||
{% if page.summary %}
|
||||
<p class="terminal__summary">{{ page.summary }}</p>
|
||||
{% endif %}
|
||||
|
||||
{% if page.read_when %}
|
||||
<details class="terminal__meta">
|
||||
<summary>Read when…</summary>
|
||||
<ul>
|
||||
{% for hint in page.read_when %}
|
||||
<li>{{ hint }}</li>
|
||||
{% endfor %}
|
||||
</ul>
|
||||
</details>
|
||||
{% endif %}
|
||||
|
||||
<article class="markdown">
|
||||
{{ content }}
|
||||
</article>
|
||||
|
||||
<footer class="terminal__footer" role="contentinfo">
|
||||
<div class="footer__line">
|
||||
<span class="footer__sig">openclaw.ai</span>
|
||||
<span class="footer__sep">·</span>
|
||||
<a href="https://github.com/openclaw/openclaw">source</a>
|
||||
<span class="footer__sep">·</span>
|
||||
<a href="https://github.com/openclaw/openclaw/releases">releases</a>
|
||||
</div>
|
||||
<div class="footer__hint" aria-hidden="true">
|
||||
tip: press <kbd>F2</kbd> (Mac: <kbd>fn</kbd>+<kbd>F2</kbd>) to flip
|
||||
the universe
|
||||
</div>
|
||||
<div class="footer__actions">
|
||||
<button
|
||||
class="theme-toggle"
|
||||
type="button"
|
||||
data-theme-toggle
|
||||
aria-label="Toggle theme (F2; on Mac: fn+F2)"
|
||||
aria-pressed="false"
|
||||
>
|
||||
<span class="theme-toggle__key">F2</span>
|
||||
<span class="theme-toggle__label" data-theme-label>theme</span>
|
||||
</button>
|
||||
</div>
|
||||
</footer>
|
||||
</div>
|
||||
</main>
|
||||
</body>
|
||||
</html>
|
||||
@@ -1,667 +0,0 @@
|
||||
(() => {
|
||||
if (document.getElementById("docs-chat-root")) return;
|
||||
|
||||
// Determine if we're on the docs site or embedded elsewhere
|
||||
const hostname = window.location.hostname;
|
||||
const isDocsSite = hostname === "localhost" || hostname === "127.0.0.1" ||
|
||||
hostname.includes("docs.openclaw") || hostname.endsWith(".mintlify.app");
|
||||
const assetsBase = isDocsSite ? "" : "https://docs.openclaw.ai";
|
||||
const apiBase = "https://claw-api.openknot.ai/api";
|
||||
|
||||
// Load marked for markdown rendering (via CDN)
|
||||
let markedReady = false;
|
||||
const loadMarkdownLib = () => {
|
||||
if (window.marked) {
|
||||
markedReady = true;
|
||||
return;
|
||||
}
|
||||
const script = document.createElement("script");
|
||||
script.src = "https://cdn.jsdelivr.net/npm/marked@15.0.6/marked.min.js";
|
||||
script.onload = () => {
|
||||
if (window.marked) {
|
||||
markedReady = true;
|
||||
}
|
||||
};
|
||||
script.onerror = () => console.warn("Failed to load marked library");
|
||||
document.head.appendChild(script);
|
||||
};
|
||||
loadMarkdownLib();
|
||||
|
||||
// Markdown renderer with fallback before module loads
|
||||
const renderMarkdown = (text) => {
|
||||
if (markedReady && window.marked) {
|
||||
// Configure marked for security: disable HTML pass-through
|
||||
const html = window.marked.parse(text, { async: false, gfm: true, breaks: true });
|
||||
// Open links in new tab by rewriting <a> tags
|
||||
return html.replace(/<a href="/g, '<a target="_blank" rel="noopener" href="');
|
||||
}
|
||||
// Fallback: escape HTML and preserve newlines
|
||||
return text
|
||||
.replace(/&/g, "&")
|
||||
.replace(/</g, "<")
|
||||
.replace(/>/g, ">")
|
||||
.replace(/\n/g, "<br>");
|
||||
};
|
||||
|
||||
const style = document.createElement("style");
|
||||
style.textContent = `
|
||||
#docs-chat-root { position: fixed; right: 20px; bottom: 20px; z-index: 9999; font-family: var(--font-body, system-ui, -apple-system, sans-serif); }
|
||||
#docs-chat-root.docs-chat-expanded { right: 0; bottom: 0; top: 0; }
|
||||
/* Thin scrollbar styling */
|
||||
#docs-chat-root ::-webkit-scrollbar { width: 6px; height: 6px; }
|
||||
#docs-chat-root ::-webkit-scrollbar-track { background: transparent; }
|
||||
#docs-chat-root ::-webkit-scrollbar-thumb { background: var(--docs-chat-panel-border); border-radius: 3px; }
|
||||
#docs-chat-root ::-webkit-scrollbar-thumb:hover { background: var(--docs-chat-muted); }
|
||||
#docs-chat-root * { scrollbar-width: thin; scrollbar-color: var(--docs-chat-panel-border) transparent; }
|
||||
:root {
|
||||
--docs-chat-accent: var(--accent, #ff7d60);
|
||||
--docs-chat-text: #1a1a1a;
|
||||
--docs-chat-muted: #555;
|
||||
--docs-chat-panel: rgba(255, 255, 255, 0.92);
|
||||
--docs-chat-panel-border: rgba(0, 0, 0, 0.1);
|
||||
--docs-chat-surface: rgba(250, 250, 250, 0.95);
|
||||
--docs-chat-shadow: 0 18px 50px rgba(0,0,0,0.15);
|
||||
--docs-chat-code-bg: rgba(0, 0, 0, 0.05);
|
||||
--docs-chat-assistant-bg: #f5f5f5;
|
||||
}
|
||||
html[data-theme="dark"] {
|
||||
--docs-chat-text: #e8e8e8;
|
||||
--docs-chat-muted: #aaa;
|
||||
--docs-chat-panel: rgba(28, 28, 30, 0.95);
|
||||
--docs-chat-panel-border: rgba(255, 255, 255, 0.12);
|
||||
--docs-chat-surface: rgba(38, 38, 40, 0.95);
|
||||
--docs-chat-shadow: 0 18px 50px rgba(0,0,0,0.5);
|
||||
--docs-chat-code-bg: rgba(255, 255, 255, 0.08);
|
||||
--docs-chat-assistant-bg: #2a2a2c;
|
||||
}
|
||||
#docs-chat-button {
|
||||
display: inline-flex;
|
||||
align-items: center;
|
||||
gap: 10px;
|
||||
background: linear-gradient(140deg, rgba(255,90,54,0.25), rgba(255,90,54,0.06));
|
||||
color: var(--docs-chat-text);
|
||||
border: 1px solid rgba(255,90,54,0.4);
|
||||
border-radius: 999px;
|
||||
padding: 10px 14px;
|
||||
cursor: pointer;
|
||||
box-shadow: 0 8px 30px rgba(255,90,54, 0.08);
|
||||
backdrop-filter: blur(12px);
|
||||
-webkit-backdrop-filter: blur(12px);
|
||||
font-family: var(--font-pixel, var(--font-body, system-ui, sans-serif));
|
||||
}
|
||||
#docs-chat-button span { font-weight: 600; letter-spacing: 0.04em; font-size: 14px; }
|
||||
.docs-chat-logo { width: 20px; height: 20px; }
|
||||
#docs-chat-panel {
|
||||
width: min(440px, calc(100vw - 40px));
|
||||
height: min(696px, calc(100vh - 80px));
|
||||
background: var(--docs-chat-panel);
|
||||
color: var(--docs-chat-text);
|
||||
border-radius: 16px;
|
||||
border: 1px solid var(--docs-chat-panel-border);
|
||||
box-shadow: var(--docs-chat-shadow);
|
||||
display: none;
|
||||
flex-direction: column;
|
||||
overflow: hidden;
|
||||
backdrop-filter: blur(16px);
|
||||
-webkit-backdrop-filter: blur(16px);
|
||||
}
|
||||
#docs-chat-root.docs-chat-expanded #docs-chat-panel {
|
||||
width: min(512px, 100vw);
|
||||
height: 100vh;
|
||||
height: 100dvh;
|
||||
border-radius: 18px 0 0 18px;
|
||||
padding-top: env(safe-area-inset-top, 0);
|
||||
padding-bottom: env(safe-area-inset-bottom, 0);
|
||||
}
|
||||
@media (max-width: 520px) {
|
||||
#docs-chat-root.docs-chat-expanded #docs-chat-panel {
|
||||
width: 100vw;
|
||||
border-radius: 0;
|
||||
}
|
||||
#docs-chat-root.docs-chat-expanded { right: 0; left: 0; bottom: 0; top: 0; }
|
||||
}
|
||||
#docs-chat-header {
|
||||
padding: 12px 14px;
|
||||
font-weight: 600;
|
||||
font-family: var(--font-pixel, var(--font-body, system-ui, sans-serif));
|
||||
letter-spacing: 0.03em;
|
||||
border-bottom: 1px solid var(--docs-chat-panel-border);
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
#docs-chat-header-title { display: inline-flex; align-items: center; gap: 8px; }
|
||||
#docs-chat-header-title span { color: var(--docs-chat-text); font-size: 15px; }
|
||||
#docs-chat-header-actions { display: inline-flex; align-items: center; gap: 6px; }
|
||||
.docs-chat-icon-button {
|
||||
border: 1px solid var(--docs-chat-panel-border);
|
||||
background: transparent;
|
||||
color: inherit;
|
||||
border-radius: 8px;
|
||||
width: 30px;
|
||||
height: 30px;
|
||||
cursor: pointer;
|
||||
font-size: 16px;
|
||||
line-height: 1;
|
||||
}
|
||||
#docs-chat-messages { flex: 1; padding: 12px 14px; overflow: auto; background: transparent; }
|
||||
#docs-chat-input {
|
||||
display: flex;
|
||||
gap: 8px;
|
||||
padding: 12px 14px;
|
||||
border-top: 1px solid var(--docs-chat-panel-border);
|
||||
background: var(--docs-chat-surface);
|
||||
backdrop-filter: blur(10px);
|
||||
-webkit-backdrop-filter: blur(10px);
|
||||
}
|
||||
#docs-chat-input textarea {
|
||||
flex: 1;
|
||||
resize: none;
|
||||
border: 1px solid var(--docs-chat-panel-border);
|
||||
border-radius: 10px;
|
||||
padding: 9px 10px;
|
||||
font-size: 14px;
|
||||
line-height: 1.5;
|
||||
font-family: inherit;
|
||||
color: var(--docs-chat-text);
|
||||
background: var(--docs-chat-surface);
|
||||
min-height: 42px;
|
||||
max-height: 120px;
|
||||
overflow-y: auto;
|
||||
}
|
||||
#docs-chat-input textarea::placeholder { color: var(--docs-chat-muted); }
|
||||
#docs-chat-send {
|
||||
background: var(--docs-chat-accent);
|
||||
color: #fff;
|
||||
border: none;
|
||||
border-radius: 10px;
|
||||
padding: 8px 14px;
|
||||
cursor: pointer;
|
||||
font-weight: 600;
|
||||
font-family: inherit;
|
||||
font-size: 14px;
|
||||
transition: opacity 0.15s ease;
|
||||
}
|
||||
#docs-chat-send:hover { opacity: 0.9; }
|
||||
#docs-chat-send:active { opacity: 0.8; }
|
||||
.docs-chat-bubble {
|
||||
margin-bottom: 10px;
|
||||
padding: 10px 14px;
|
||||
border-radius: 12px;
|
||||
font-size: 14px;
|
||||
line-height: 1.6;
|
||||
max-width: 92%;
|
||||
}
|
||||
.docs-chat-user {
|
||||
background: rgba(255, 125, 96, 0.15);
|
||||
color: var(--docs-chat-text);
|
||||
border: 1px solid rgba(255, 125, 96, 0.3);
|
||||
align-self: flex-end;
|
||||
white-space: pre-wrap;
|
||||
margin-left: auto;
|
||||
}
|
||||
html[data-theme="dark"] .docs-chat-user {
|
||||
background: rgba(255, 125, 96, 0.18);
|
||||
border-color: rgba(255, 125, 96, 0.35);
|
||||
}
|
||||
.docs-chat-assistant {
|
||||
background: var(--docs-chat-assistant-bg);
|
||||
color: var(--docs-chat-text);
|
||||
border: 1px solid var(--docs-chat-panel-border);
|
||||
}
|
||||
/* Markdown content styling for chat bubbles */
|
||||
.docs-chat-assistant p { margin: 0 0 10px 0; }
|
||||
.docs-chat-assistant p:last-child { margin-bottom: 0; }
|
||||
.docs-chat-assistant code {
|
||||
background: var(--docs-chat-code-bg);
|
||||
padding: 2px 6px;
|
||||
border-radius: 5px;
|
||||
font-family: ui-monospace, SFMono-Regular, Menlo, Monaco, Consolas, monospace;
|
||||
font-size: 0.9em;
|
||||
}
|
||||
.docs-chat-assistant pre {
|
||||
background: var(--docs-chat-code-bg);
|
||||
padding: 10px 12px;
|
||||
border-radius: 8px;
|
||||
overflow-x: auto;
|
||||
margin: 6px 0;
|
||||
font-size: 0.9em;
|
||||
max-width: 100%;
|
||||
white-space: pre;
|
||||
word-wrap: normal;
|
||||
}
|
||||
.docs-chat-assistant pre::-webkit-scrollbar-thumb { background: transparent; }
|
||||
.docs-chat-assistant pre:hover::-webkit-scrollbar-thumb { background: var(--docs-chat-panel-border); }
|
||||
@media (hover: none) {
|
||||
.docs-chat-assistant pre { -webkit-overflow-scrolling: touch; }
|
||||
.docs-chat-assistant pre::-webkit-scrollbar-thumb { background: var(--docs-chat-panel-border); }
|
||||
}
|
||||
.docs-chat-assistant pre code {
|
||||
background: transparent;
|
||||
padding: 0;
|
||||
font-size: inherit;
|
||||
white-space: pre;
|
||||
word-wrap: normal;
|
||||
display: block;
|
||||
}
|
||||
/* Compact single-line code blocks */
|
||||
.docs-chat-assistant pre.compact {
|
||||
margin: 4px 0;
|
||||
padding: 6px 10px;
|
||||
}
|
||||
/* Longer code blocks with copy button need extra top padding */
|
||||
.docs-chat-assistant pre:not(.compact) {
|
||||
padding-top: 28px;
|
||||
}
|
||||
.docs-chat-assistant a {
|
||||
color: var(--docs-chat-accent);
|
||||
text-decoration: underline;
|
||||
text-underline-offset: 2px;
|
||||
}
|
||||
.docs-chat-assistant a:hover { opacity: 0.8; }
|
||||
.docs-chat-assistant ul, .docs-chat-assistant ol {
|
||||
margin: 8px 0;
|
||||
padding-left: 18px;
|
||||
list-style: none;
|
||||
}
|
||||
.docs-chat-assistant li {
|
||||
margin: 4px 0;
|
||||
position: relative;
|
||||
padding-left: 14px;
|
||||
}
|
||||
.docs-chat-assistant li::before {
|
||||
content: "•";
|
||||
position: absolute;
|
||||
left: 0;
|
||||
color: var(--docs-chat-muted);
|
||||
}
|
||||
.docs-chat-assistant strong { font-weight: 600; }
|
||||
.docs-chat-assistant em { font-style: italic; }
|
||||
.docs-chat-assistant h1, .docs-chat-assistant h2, .docs-chat-assistant h3 {
|
||||
font-weight: 600;
|
||||
margin: 12px 0 6px 0;
|
||||
line-height: 1.3;
|
||||
}
|
||||
.docs-chat-assistant h1 { font-size: 1.2em; }
|
||||
.docs-chat-assistant h2 { font-size: 1.1em; }
|
||||
.docs-chat-assistant h3 { font-size: 1.05em; }
|
||||
.docs-chat-assistant blockquote {
|
||||
border-left: 3px solid var(--docs-chat-accent);
|
||||
margin: 10px 0;
|
||||
padding: 4px 12px;
|
||||
color: var(--docs-chat-muted);
|
||||
background: var(--docs-chat-code-bg);
|
||||
border-radius: 0 6px 6px 0;
|
||||
}
|
||||
.docs-chat-assistant hr {
|
||||
border: none;
|
||||
height: 1px;
|
||||
background: var(--docs-chat-panel-border);
|
||||
margin: 12px 0;
|
||||
}
|
||||
/* Copy buttons */
|
||||
.docs-chat-assistant { position: relative; padding-top: 28px; }
|
||||
.docs-chat-copy-response {
|
||||
position: absolute;
|
||||
top: 8px;
|
||||
right: 8px;
|
||||
background: var(--docs-chat-surface);
|
||||
border: 1px solid var(--docs-chat-panel-border);
|
||||
border-radius: 5px;
|
||||
padding: 4px 8px;
|
||||
font-size: 11px;
|
||||
cursor: pointer;
|
||||
color: var(--docs-chat-muted);
|
||||
transition: color 0.15s ease, background 0.15s ease;
|
||||
}
|
||||
.docs-chat-copy-response:hover {
|
||||
color: var(--docs-chat-text);
|
||||
background: var(--docs-chat-code-bg);
|
||||
}
|
||||
.docs-chat-assistant pre {
|
||||
position: relative;
|
||||
}
|
||||
.docs-chat-copy-code {
|
||||
position: absolute;
|
||||
top: 8px;
|
||||
right: 8px;
|
||||
background: var(--docs-chat-surface);
|
||||
border: 1px solid var(--docs-chat-panel-border);
|
||||
border-radius: 4px;
|
||||
padding: 3px 7px;
|
||||
font-size: 10px;
|
||||
cursor: pointer;
|
||||
color: var(--docs-chat-muted);
|
||||
transition: color 0.15s ease, background 0.15s ease;
|
||||
z-index: 1;
|
||||
}
|
||||
.docs-chat-copy-code:hover {
|
||||
color: var(--docs-chat-text);
|
||||
background: var(--docs-chat-code-bg);
|
||||
}
|
||||
/* Resize handle - left edge of expanded panel */
|
||||
#docs-chat-resize-handle {
|
||||
position: absolute;
|
||||
left: 0;
|
||||
top: 0;
|
||||
bottom: 0;
|
||||
width: 6px;
|
||||
cursor: ew-resize;
|
||||
z-index: 10;
|
||||
display: none;
|
||||
}
|
||||
#docs-chat-root.docs-chat-expanded #docs-chat-resize-handle { display: block; }
|
||||
#docs-chat-resize-handle::after {
|
||||
content: "";
|
||||
position: absolute;
|
||||
left: 1px;
|
||||
top: 50%;
|
||||
transform: translateY(-50%);
|
||||
width: 4px;
|
||||
height: 40px;
|
||||
border-radius: 2px;
|
||||
background: var(--docs-chat-panel-border);
|
||||
opacity: 0;
|
||||
transition: opacity 0.15s ease, background 0.15s ease;
|
||||
}
|
||||
#docs-chat-resize-handle:hover::after,
|
||||
#docs-chat-resize-handle.docs-chat-dragging::after {
|
||||
opacity: 1;
|
||||
background: var(--docs-chat-accent);
|
||||
}
|
||||
@media (max-width: 520px) {
|
||||
#docs-chat-resize-handle { display: none !important; }
|
||||
}
|
||||
`;
|
||||
document.head.appendChild(style);
|
||||
|
||||
const root = document.createElement("div");
|
||||
root.id = "docs-chat-root";
|
||||
|
||||
const button = document.createElement("button");
|
||||
button.id = "docs-chat-button";
|
||||
button.type = "button";
|
||||
button.innerHTML =
|
||||
`<img class="docs-chat-logo" src="${assetsBase}/assets/pixel-lobster.svg" alt="OpenClaw">` +
|
||||
`<span>Ask Molty</span>`;
|
||||
|
||||
const panel = document.createElement("div");
|
||||
panel.id = "docs-chat-panel";
|
||||
panel.style.display = "none";
|
||||
|
||||
// Resize handle for expandable sidebar width (desktop only)
|
||||
const resizeHandle = document.createElement("div");
|
||||
resizeHandle.id = "docs-chat-resize-handle";
|
||||
|
||||
const header = document.createElement("div");
|
||||
header.id = "docs-chat-header";
|
||||
header.innerHTML =
|
||||
`<div id="docs-chat-header-title">` +
|
||||
`<img class="docs-chat-logo" src="${assetsBase}/assets/pixel-lobster.svg" alt="OpenClaw">` +
|
||||
`<span>OpenClaw Docs</span>` +
|
||||
`</div>` +
|
||||
`<div id="docs-chat-header-actions"></div>`;
|
||||
const headerActions = header.querySelector("#docs-chat-header-actions");
|
||||
const expand = document.createElement("button");
|
||||
expand.type = "button";
|
||||
expand.className = "docs-chat-icon-button";
|
||||
expand.setAttribute("aria-label", "Expand");
|
||||
expand.textContent = "⤢";
|
||||
const clear = document.createElement("button");
|
||||
clear.type = "button";
|
||||
clear.className = "docs-chat-icon-button";
|
||||
clear.setAttribute("aria-label", "Clear chat");
|
||||
clear.textContent = "⌫";
|
||||
const close = document.createElement("button");
|
||||
close.type = "button";
|
||||
close.className = "docs-chat-icon-button";
|
||||
close.setAttribute("aria-label", "Close");
|
||||
close.textContent = "×";
|
||||
headerActions.appendChild(expand);
|
||||
headerActions.appendChild(clear);
|
||||
headerActions.appendChild(close);
|
||||
|
||||
const messages = document.createElement("div");
|
||||
messages.id = "docs-chat-messages";
|
||||
|
||||
const inputWrap = document.createElement("div");
|
||||
inputWrap.id = "docs-chat-input";
|
||||
const textarea = document.createElement("textarea");
|
||||
textarea.rows = 1;
|
||||
textarea.placeholder = "Ask about OpenClaw Docs...";
|
||||
|
||||
// Auto-expand textarea as user types (up to max-height set in CSS)
|
||||
const autoExpand = () => {
|
||||
textarea.style.height = "auto";
|
||||
textarea.style.height = Math.min(textarea.scrollHeight, 224) + "px";
|
||||
};
|
||||
textarea.addEventListener("input", autoExpand);
|
||||
|
||||
const send = document.createElement("button");
|
||||
send.id = "docs-chat-send";
|
||||
send.type = "button";
|
||||
send.textContent = "Send";
|
||||
|
||||
inputWrap.appendChild(textarea);
|
||||
inputWrap.appendChild(send);
|
||||
|
||||
panel.appendChild(resizeHandle);
|
||||
panel.appendChild(header);
|
||||
panel.appendChild(messages);
|
||||
panel.appendChild(inputWrap);
|
||||
|
||||
root.appendChild(button);
|
||||
root.appendChild(panel);
|
||||
document.body.appendChild(root);
|
||||
|
||||
// Add copy buttons to assistant bubble
|
||||
const addCopyButtons = (bubble, rawText) => {
|
||||
// Add copy response button
|
||||
const copyResponse = document.createElement("button");
|
||||
copyResponse.className = "docs-chat-copy-response";
|
||||
copyResponse.textContent = "Copy";
|
||||
copyResponse.type = "button";
|
||||
copyResponse.addEventListener("click", async () => {
|
||||
try {
|
||||
await navigator.clipboard.writeText(rawText);
|
||||
copyResponse.textContent = "Copied!";
|
||||
setTimeout(() => (copyResponse.textContent = "Copy"), 1500);
|
||||
} catch (e) {
|
||||
copyResponse.textContent = "Failed";
|
||||
}
|
||||
});
|
||||
bubble.appendChild(copyResponse);
|
||||
|
||||
// Add copy buttons to code blocks (skip short/single-line blocks)
|
||||
bubble.querySelectorAll("pre").forEach((pre) => {
|
||||
const code = pre.querySelector("code") || pre;
|
||||
const text = code.textContent || "";
|
||||
const lineCount = text.split("\n").length;
|
||||
const isShort = lineCount <= 2 && text.length < 100;
|
||||
|
||||
if (isShort) {
|
||||
pre.classList.add("compact");
|
||||
return; // Skip copy button for compact blocks
|
||||
}
|
||||
|
||||
const copyCode = document.createElement("button");
|
||||
copyCode.className = "docs-chat-copy-code";
|
||||
copyCode.textContent = "Copy";
|
||||
copyCode.type = "button";
|
||||
copyCode.addEventListener("click", async (e) => {
|
||||
e.stopPropagation();
|
||||
try {
|
||||
await navigator.clipboard.writeText(text);
|
||||
copyCode.textContent = "Copied!";
|
||||
setTimeout(() => (copyCode.textContent = "Copy"), 1500);
|
||||
} catch (err) {
|
||||
copyCode.textContent = "Failed";
|
||||
}
|
||||
});
|
||||
pre.appendChild(copyCode);
|
||||
});
|
||||
};
|
||||
|
||||
const addBubble = (text, role, isMarkdown = false) => {
|
||||
const bubble = document.createElement("div");
|
||||
bubble.className =
|
||||
"docs-chat-bubble " +
|
||||
(role === "user" ? "docs-chat-user" : "docs-chat-assistant");
|
||||
if (isMarkdown && role === "assistant") {
|
||||
bubble.innerHTML = renderMarkdown(text);
|
||||
} else {
|
||||
bubble.textContent = text;
|
||||
}
|
||||
messages.appendChild(bubble);
|
||||
messages.scrollTop = messages.scrollHeight;
|
||||
return bubble;
|
||||
};
|
||||
|
||||
let isExpanded = false;
|
||||
let customWidth = null; // User-set width via drag
|
||||
const MIN_WIDTH = 320;
|
||||
const MAX_WIDTH = 800;
|
||||
|
||||
// Drag-to-resize logic
|
||||
let isDragging = false;
|
||||
let startX, startWidth;
|
||||
|
||||
resizeHandle.addEventListener("mousedown", (e) => {
|
||||
if (!isExpanded) return;
|
||||
isDragging = true;
|
||||
startX = e.clientX;
|
||||
startWidth = panel.offsetWidth;
|
||||
resizeHandle.classList.add("docs-chat-dragging");
|
||||
document.body.style.cursor = "ew-resize";
|
||||
document.body.style.userSelect = "none";
|
||||
e.preventDefault();
|
||||
});
|
||||
|
||||
document.addEventListener("mousemove", (e) => {
|
||||
if (!isDragging) return;
|
||||
// Panel is on right, so dragging left increases width
|
||||
const delta = startX - e.clientX;
|
||||
const newWidth = Math.min(MAX_WIDTH, Math.max(MIN_WIDTH, startWidth + delta));
|
||||
customWidth = newWidth;
|
||||
panel.style.width = newWidth + "px";
|
||||
});
|
||||
|
||||
document.addEventListener("mouseup", () => {
|
||||
if (!isDragging) return;
|
||||
isDragging = false;
|
||||
resizeHandle.classList.remove("docs-chat-dragging");
|
||||
document.body.style.cursor = "";
|
||||
document.body.style.userSelect = "";
|
||||
});
|
||||
|
||||
const setOpen = (isOpen) => {
|
||||
panel.style.display = isOpen ? "flex" : "none";
|
||||
button.style.display = isOpen ? "none" : "inline-flex";
|
||||
root.classList.toggle("docs-chat-expanded", isOpen && isExpanded);
|
||||
if (!isOpen) {
|
||||
panel.style.width = ""; // Reset to CSS default when closed
|
||||
} else if (isExpanded && customWidth) {
|
||||
panel.style.width = customWidth + "px";
|
||||
}
|
||||
if (isOpen) textarea.focus();
|
||||
};
|
||||
|
||||
const setExpanded = (next) => {
|
||||
isExpanded = next;
|
||||
expand.textContent = isExpanded ? "⤡" : "⤢";
|
||||
expand.setAttribute("aria-label", isExpanded ? "Collapse" : "Expand");
|
||||
if (panel.style.display !== "none") {
|
||||
root.classList.toggle("docs-chat-expanded", isExpanded);
|
||||
if (isExpanded && customWidth) {
|
||||
panel.style.width = customWidth + "px";
|
||||
} else if (!isExpanded) {
|
||||
panel.style.width = ""; // Reset to CSS default
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
button.addEventListener("click", () => setOpen(true));
|
||||
expand.addEventListener("click", () => setExpanded(!isExpanded));
|
||||
clear.addEventListener("click", () => {
|
||||
messages.innerHTML = "";
|
||||
});
|
||||
close.addEventListener("click", () => {
|
||||
setOpen(false);
|
||||
root.classList.remove("docs-chat-expanded");
|
||||
});
|
||||
|
||||
const sendMessage = async () => {
|
||||
const text = textarea.value.trim();
|
||||
if (!text) return;
|
||||
textarea.value = "";
|
||||
textarea.style.height = "auto"; // Reset height after sending
|
||||
addBubble(text, "user");
|
||||
const assistantBubble = addBubble("...", "assistant");
|
||||
assistantBubble.innerHTML = "";
|
||||
|
||||
let fullText = "";
|
||||
try {
|
||||
const response = await fetch(`${apiBase}/chat`, {
|
||||
method: "POST",
|
||||
headers: { "Content-Type": "application/json" },
|
||||
body: JSON.stringify({ message: text }),
|
||||
});
|
||||
|
||||
// Handle rate limiting
|
||||
if (response.status === 429) {
|
||||
const retryAfter = response.headers.get("Retry-After") || "60";
|
||||
fullText = `You're asking questions too quickly. Please wait ${retryAfter} seconds before trying again.`;
|
||||
assistantBubble.innerHTML = renderMarkdown(fullText);
|
||||
addCopyButtons(assistantBubble, fullText);
|
||||
return;
|
||||
}
|
||||
|
||||
// Handle other errors
|
||||
if (!response.ok) {
|
||||
try {
|
||||
const errorData = await response.json();
|
||||
fullText = errorData.error || "Something went wrong. Please try again.";
|
||||
} catch {
|
||||
fullText = "Something went wrong. Please try again.";
|
||||
}
|
||||
assistantBubble.innerHTML = renderMarkdown(fullText);
|
||||
addCopyButtons(assistantBubble, fullText);
|
||||
return;
|
||||
}
|
||||
|
||||
if (!response.body) {
|
||||
fullText = await response.text();
|
||||
assistantBubble.innerHTML = renderMarkdown(fullText);
|
||||
addCopyButtons(assistantBubble, fullText);
|
||||
return;
|
||||
}
|
||||
const reader = response.body.getReader();
|
||||
const decoder = new TextDecoder();
|
||||
while (true) {
|
||||
const { value, done } = await reader.read();
|
||||
if (done) break;
|
||||
fullText += decoder.decode(value, { stream: true });
|
||||
// Re-render markdown on each chunk for live preview
|
||||
assistantBubble.innerHTML = renderMarkdown(fullText);
|
||||
messages.scrollTop = messages.scrollHeight;
|
||||
}
|
||||
// Flush any remaining buffered bytes (partial UTF-8 sequences)
|
||||
fullText += decoder.decode();
|
||||
assistantBubble.innerHTML = renderMarkdown(fullText);
|
||||
// Add copy buttons after streaming completes
|
||||
addCopyButtons(assistantBubble, fullText);
|
||||
} catch (err) {
|
||||
fullText = "Failed to reach docs chat API.";
|
||||
assistantBubble.innerHTML = renderMarkdown(fullText);
|
||||
addCopyButtons(assistantBubble, fullText);
|
||||
}
|
||||
};
|
||||
|
||||
send.addEventListener("click", sendMessage);
|
||||
textarea.addEventListener("keydown", (event) => {
|
||||
if (event.key === "Enter" && !event.shiftKey) {
|
||||
event.preventDefault();
|
||||
sendMessage();
|
||||
}
|
||||
});
|
||||
})();
|
||||
BIN
docs/assets/macos-onboarding/01-macos-warning.jpeg
Normal file
BIN
docs/assets/macos-onboarding/01-macos-warning.jpeg
Normal file
Binary file not shown.
|
After Width: | Height: | Size: 155 KiB |
BIN
docs/assets/macos-onboarding/02-local-networks.jpeg
Normal file
BIN
docs/assets/macos-onboarding/02-local-networks.jpeg
Normal file
Binary file not shown.
|
After Width: | Height: | Size: 162 KiB |
BIN
docs/assets/macos-onboarding/03-security-notice.png
Normal file
BIN
docs/assets/macos-onboarding/03-security-notice.png
Normal file
Binary file not shown.
|
After Width: | Height: | Size: 312 KiB |
BIN
docs/assets/macos-onboarding/04-choose-gateway.png
Normal file
BIN
docs/assets/macos-onboarding/04-choose-gateway.png
Normal file
Binary file not shown.
|
After Width: | Height: | Size: 312 KiB |
BIN
docs/assets/macos-onboarding/05-permissions.png
Normal file
BIN
docs/assets/macos-onboarding/05-permissions.png
Normal file
Binary file not shown.
|
After Width: | Height: | Size: 362 KiB |
@@ -1,179 +0,0 @@
|
||||
.markdown {
|
||||
margin-top: 18px;
|
||||
line-height: 1.7;
|
||||
}
|
||||
|
||||
.mdx-content > h1:first-of-type {
|
||||
display: none;
|
||||
}
|
||||
|
||||
.markdown h1,
|
||||
.markdown h2,
|
||||
.markdown h3,
|
||||
.markdown h4 {
|
||||
font-family: var(--font-pixel);
|
||||
letter-spacing: 0.04em;
|
||||
line-height: 1.15;
|
||||
}
|
||||
|
||||
.markdown h1 {
|
||||
font-size: clamp(28px, 4vw, 44px);
|
||||
margin: 26px 0 10px;
|
||||
}
|
||||
|
||||
.markdown h2 {
|
||||
font-size: 22px;
|
||||
margin: 26px 0 10px;
|
||||
}
|
||||
|
||||
.markdown h3 {
|
||||
font-size: 18px;
|
||||
margin: 22px 0 8px;
|
||||
}
|
||||
|
||||
.markdown p {
|
||||
margin: 0 0 14px;
|
||||
}
|
||||
|
||||
.markdown a {
|
||||
color: var(--link);
|
||||
text-decoration: none;
|
||||
border-bottom: 1px dotted color-mix(in oklab, var(--link) 65%, transparent);
|
||||
}
|
||||
|
||||
.markdown a:hover {
|
||||
color: var(--link2);
|
||||
border-bottom-color: color-mix(in oklab, var(--link2) 75%, transparent);
|
||||
}
|
||||
|
||||
.markdown hr {
|
||||
border: 0;
|
||||
height: 1px;
|
||||
background: linear-gradient(
|
||||
90deg,
|
||||
transparent,
|
||||
color-mix(in oklab, var(--frame-border) 30%, transparent),
|
||||
transparent
|
||||
);
|
||||
margin: 26px 0;
|
||||
}
|
||||
|
||||
.markdown blockquote {
|
||||
margin: 18px 0;
|
||||
padding: 14px 14px;
|
||||
border-radius: var(--radius-sm);
|
||||
background: color-mix(in oklab, var(--panel) 70%, transparent);
|
||||
border-left: 6px solid color-mix(in oklab, var(--accent) 60%, transparent);
|
||||
color: var(--muted);
|
||||
}
|
||||
|
||||
.markdown ul,
|
||||
.markdown ol {
|
||||
margin: 0 0 14px 22px;
|
||||
}
|
||||
|
||||
.markdown li {
|
||||
margin: 4px 0;
|
||||
}
|
||||
|
||||
.markdown img {
|
||||
max-width: 100%;
|
||||
height: auto;
|
||||
border-radius: 12px;
|
||||
border: 1px solid color-mix(in oklab, var(--frame-border) 20%, transparent);
|
||||
box-shadow: 0 12px 0 -8px rgba(0, 0, 0, 0.18);
|
||||
}
|
||||
|
||||
.showcase-link {
|
||||
position: relative;
|
||||
display: inline-flex;
|
||||
align-items: center;
|
||||
gap: 6px;
|
||||
}
|
||||
|
||||
.showcase-preview {
|
||||
position: absolute;
|
||||
left: 50%;
|
||||
top: 100%;
|
||||
width: min(420px, 80vw);
|
||||
padding: 8px;
|
||||
border-radius: 14px;
|
||||
background: color-mix(in oklab, var(--panel) 92%, transparent);
|
||||
border: 1px solid color-mix(in oklab, var(--frame-border) 30%, transparent);
|
||||
box-shadow: 0 18px 40px -18px rgba(0, 0, 0, 0.55);
|
||||
transform: translate(-50%, 10px) scale(0.98);
|
||||
opacity: 0;
|
||||
visibility: hidden;
|
||||
pointer-events: none;
|
||||
z-index: 20;
|
||||
transition: opacity 0.18s ease, transform 0.18s ease, visibility 0.18s ease;
|
||||
}
|
||||
|
||||
.showcase-preview img {
|
||||
width: 100%;
|
||||
height: auto;
|
||||
border-radius: 10px;
|
||||
border: 1px solid color-mix(in oklab, var(--frame-border) 25%, transparent);
|
||||
box-shadow: none;
|
||||
}
|
||||
|
||||
.showcase-link:hover .showcase-preview,
|
||||
.showcase-link:focus-within .showcase-preview {
|
||||
opacity: 1;
|
||||
visibility: visible;
|
||||
transform: translate(-50%, 6px) scale(1);
|
||||
}
|
||||
|
||||
@media (hover: none) {
|
||||
.showcase-preview {
|
||||
display: none;
|
||||
}
|
||||
}
|
||||
|
||||
.markdown code {
|
||||
font-family: var(--font-body);
|
||||
font-size: 0.95em;
|
||||
padding: 0.15em 0.35em;
|
||||
border-radius: 8px;
|
||||
background: color-mix(in oklab, var(--panel) 70%, var(--code-bg));
|
||||
border: 1px solid color-mix(in oklab, var(--frame-border) 18%, transparent);
|
||||
}
|
||||
|
||||
.markdown pre {
|
||||
background: var(--code-bg);
|
||||
color: var(--code-fg);
|
||||
padding: 14px 14px;
|
||||
border-radius: var(--radius-sm);
|
||||
border: 1px solid color-mix(in oklab, var(--frame-border) 18%, transparent);
|
||||
overflow-x: auto;
|
||||
box-shadow: inset 0 0 0 1px color-mix(in oklab, var(--code-accent) 12%, transparent);
|
||||
}
|
||||
|
||||
.markdown pre code {
|
||||
background: transparent;
|
||||
border: 0;
|
||||
padding: 0;
|
||||
color: inherit;
|
||||
}
|
||||
|
||||
.markdown table {
|
||||
width: 100%;
|
||||
border-collapse: collapse;
|
||||
margin: 16px 0 22px;
|
||||
border: 1px solid color-mix(in oklab, var(--frame-border) 20%, transparent);
|
||||
border-radius: var(--radius-sm);
|
||||
overflow: hidden;
|
||||
}
|
||||
|
||||
.markdown th,
|
||||
.markdown td {
|
||||
padding: 10px 10px;
|
||||
border-bottom: 1px solid color-mix(in oklab, var(--frame-border) 15%, transparent);
|
||||
vertical-align: top;
|
||||
}
|
||||
|
||||
.markdown th {
|
||||
background: color-mix(in oklab, var(--panel2) 85%, transparent);
|
||||
font-family: var(--font-pixel);
|
||||
letter-spacing: 0.06em;
|
||||
}
|
||||
@@ -1,473 +0,0 @@
|
||||
:root {
|
||||
--font-body: "Fragment Mono", ui-monospace, SFMono-Regular, Menlo, Monaco, Consolas, "Liberation Mono", "Courier New", monospace;
|
||||
--font-pixel: "Pixelify Sans", system-ui, sans-serif;
|
||||
--radius: 14px;
|
||||
--radius-sm: 10px;
|
||||
--border: 2px;
|
||||
--shadow-px: 0 0 0 var(--border) var(--frame-border), 0 12px 0 -4px rgba(0, 0, 0, 0.25);
|
||||
--scanline-size: 6px;
|
||||
--scanline-opacity: 0.08;
|
||||
}
|
||||
|
||||
html[data-theme="light"],
|
||||
html[data-theme="auto"] {
|
||||
--bg0: #fbf4e7;
|
||||
--bg1: #fffaf0;
|
||||
--panel: #fffdf8;
|
||||
--panel2: #fff6e5;
|
||||
--text: #10221c;
|
||||
--muted: #3e5a50;
|
||||
--faint: #6b7f77;
|
||||
--link: #0f6b4c;
|
||||
--link2: #ff4f40;
|
||||
--accent: #ff4f40;
|
||||
--accent2: #00b88a;
|
||||
--frame-border: #1b2e27;
|
||||
--code-bg: #0b1713;
|
||||
--code-fg: #eafff6;
|
||||
--code-accent: #67ff9b;
|
||||
}
|
||||
|
||||
html[data-theme="dark"] {
|
||||
--bg0: #0b1a22;
|
||||
--bg1: #0a1720;
|
||||
--panel: #0e231f;
|
||||
--panel2: #102a24;
|
||||
--text: #c9eadc;
|
||||
--muted: #8ab8aa;
|
||||
--faint: #699b8d;
|
||||
--link: #6fe8c7;
|
||||
--link2: #ff7b63;
|
||||
--accent: #ff4f40;
|
||||
--accent2: #5fdfa2;
|
||||
--frame-border: #6fbfa8;
|
||||
--code-bg: #091814;
|
||||
--code-fg: #d7f5e8;
|
||||
--code-accent: #5fdfa2;
|
||||
}
|
||||
|
||||
@media (prefers-color-scheme: dark) {
|
||||
html[data-theme="auto"] {
|
||||
--bg0: #0b1a22;
|
||||
--bg1: #0a1720;
|
||||
--panel: #0e231f;
|
||||
--panel2: #102a24;
|
||||
--text: #c9eadc;
|
||||
--muted: #8ab8aa;
|
||||
--faint: #699b8d;
|
||||
--link: #6fe8c7;
|
||||
--link2: #ff7b63;
|
||||
--accent: #ff4f40;
|
||||
--accent2: #5fdfa2;
|
||||
--frame-border: #6fbfa8;
|
||||
--code-bg: #091814;
|
||||
--code-fg: #d7f5e8;
|
||||
--code-accent: #5fdfa2;
|
||||
}
|
||||
}
|
||||
|
||||
* {
|
||||
box-sizing: border-box;
|
||||
}
|
||||
|
||||
html {
|
||||
height: 100%;
|
||||
}
|
||||
|
||||
body {
|
||||
min-height: 100%;
|
||||
}
|
||||
|
||||
body {
|
||||
margin: 0;
|
||||
font-family: var(--font-body);
|
||||
color: var(--text);
|
||||
background:
|
||||
radial-gradient(1100px 700px at 20% -10%, color-mix(in oklab, var(--accent) 18%, transparent), transparent 55%),
|
||||
radial-gradient(900px 600px at 95% 10%, color-mix(in oklab, var(--accent2) 14%, transparent), transparent 60%),
|
||||
radial-gradient(900px 600px at 50% 120%, color-mix(in oklab, var(--link) 10%, transparent), transparent 55%),
|
||||
linear-gradient(180deg, var(--bg0), var(--bg1));
|
||||
overflow-x: hidden;
|
||||
}
|
||||
|
||||
body::before,
|
||||
body::after {
|
||||
display: none;
|
||||
}
|
||||
|
||||
.skip-link {
|
||||
position: absolute;
|
||||
top: 10px;
|
||||
left: 10px;
|
||||
z-index: 10;
|
||||
padding: 10px 12px;
|
||||
border-radius: 999px;
|
||||
background: var(--panel);
|
||||
color: var(--text);
|
||||
text-decoration: none;
|
||||
transform: translateY(-130%);
|
||||
box-shadow: var(--shadow-px);
|
||||
}
|
||||
|
||||
.skip-link:focus {
|
||||
transform: translateY(0);
|
||||
outline: none;
|
||||
}
|
||||
|
||||
.shell {
|
||||
position: sticky;
|
||||
top: 0;
|
||||
z-index: 100;
|
||||
padding: 22px 16px 10px;
|
||||
}
|
||||
|
||||
.shell__frame {
|
||||
max-width: 1120px;
|
||||
margin: 0 auto;
|
||||
border-radius: var(--radius);
|
||||
background:
|
||||
linear-gradient(180deg, color-mix(in oklab, var(--panel2) 88%, transparent), color-mix(in oklab, var(--panel) 92%, transparent));
|
||||
box-shadow: var(--shadow-px);
|
||||
border: var(--border) solid var(--frame-border);
|
||||
overflow: hidden;
|
||||
}
|
||||
|
||||
.shell__titlebar {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: space-between;
|
||||
gap: 12px;
|
||||
padding: 14px 14px 12px;
|
||||
background:
|
||||
linear-gradient(90deg, color-mix(in oklab, var(--accent) 26%, transparent), transparent 42%),
|
||||
linear-gradient(180deg, color-mix(in oklab, var(--panel) 90%, #000 10%), color-mix(in oklab, var(--panel2) 90%, #000 10%));
|
||||
}
|
||||
|
||||
.brand {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
gap: 12px;
|
||||
min-width: 0;
|
||||
}
|
||||
|
||||
.brand__logo {
|
||||
flex: 0 0 auto;
|
||||
width: 40px;
|
||||
height: 40px;
|
||||
image-rendering: pixelated;
|
||||
filter: drop-shadow(0 2px 0 color-mix(in oklab, var(--frame-border) 80%, transparent));
|
||||
}
|
||||
|
||||
.brand__text {
|
||||
min-width: 0;
|
||||
}
|
||||
|
||||
.brand__name {
|
||||
font-family: var(--font-pixel);
|
||||
letter-spacing: 0.14em;
|
||||
font-weight: 700;
|
||||
font-size: 18px;
|
||||
line-height: 1.1;
|
||||
text-shadow: 0 1px 0 color-mix(in oklab, var(--frame-border) 55%, transparent);
|
||||
}
|
||||
|
||||
.brand__hint {
|
||||
margin-top: 2px;
|
||||
font-size: 12px;
|
||||
color: var(--muted);
|
||||
white-space: nowrap;
|
||||
overflow: hidden;
|
||||
text-overflow: ellipsis;
|
||||
}
|
||||
|
||||
.titlebar__actions {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
gap: 10px;
|
||||
}
|
||||
|
||||
.titlebar__cta {
|
||||
display: inline-flex;
|
||||
align-items: center;
|
||||
gap: 8px;
|
||||
padding: 8px 12px 8px 10px;
|
||||
border-radius: 12px;
|
||||
background:
|
||||
linear-gradient(140deg, color-mix(in oklab, var(--accent) 10%, transparent), transparent 60%),
|
||||
color-mix(in oklab, var(--panel) 92%, transparent);
|
||||
border: var(--border) solid color-mix(in oklab, var(--frame-border) 80%, transparent);
|
||||
color: var(--text);
|
||||
text-decoration: none;
|
||||
box-shadow:
|
||||
0 6px 0 -3px rgba(0, 0, 0, 0.25),
|
||||
inset 0 0 0 1px color-mix(in oklab, var(--panel2) 55%, transparent);
|
||||
}
|
||||
|
||||
.titlebar__cta:hover {
|
||||
border-color: color-mix(in oklab, var(--accent2) 45%, transparent);
|
||||
box-shadow:
|
||||
0 0 0 2px color-mix(in oklab, var(--accent2) 30%, transparent),
|
||||
0 6px 0 -3px rgba(0, 0, 0, 0.25);
|
||||
}
|
||||
|
||||
.titlebar__cta:active {
|
||||
transform: translateY(1px);
|
||||
box-shadow: 0 4px 0 -3px rgba(0, 0, 0, 0.25);
|
||||
}
|
||||
|
||||
.titlebar__cta:focus-visible {
|
||||
outline: 3px solid color-mix(in oklab, var(--accent2) 60%, transparent);
|
||||
outline-offset: 2px;
|
||||
}
|
||||
|
||||
.titlebar__cta--accent {
|
||||
background:
|
||||
linear-gradient(120deg, color-mix(in oklab, var(--accent) 22%, transparent), transparent 70%),
|
||||
color-mix(in oklab, var(--panel) 88%, transparent);
|
||||
border-color: color-mix(in oklab, var(--accent) 60%, var(--frame-border));
|
||||
}
|
||||
|
||||
.titlebar__cta-label {
|
||||
font-family: var(--font-pixel);
|
||||
letter-spacing: 0.12em;
|
||||
font-size: 12px;
|
||||
text-transform: uppercase;
|
||||
}
|
||||
|
||||
.titlebar__cta-meta {
|
||||
display: inline-flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
height: 20px;
|
||||
padding: 0 8px;
|
||||
border-radius: 999px;
|
||||
font-size: 11px;
|
||||
text-transform: uppercase;
|
||||
letter-spacing: 0.08em;
|
||||
background: var(--code-bg);
|
||||
color: var(--code-accent);
|
||||
border: 1px solid color-mix(in oklab, var(--code-accent) 30%, transparent);
|
||||
box-shadow: inset 0 0 12px color-mix(in oklab, var(--code-accent) 25%, transparent);
|
||||
}
|
||||
|
||||
.theme-toggle {
|
||||
display: inline-flex;
|
||||
align-items: center;
|
||||
gap: 10px;
|
||||
padding: 9px 10px;
|
||||
border-radius: 12px;
|
||||
background: color-mix(in oklab, var(--panel) 92%, transparent);
|
||||
border: var(--border) solid var(--frame-border);
|
||||
color: var(--text);
|
||||
cursor: pointer;
|
||||
box-shadow: 0 6px 0 -3px rgba(0, 0, 0, 0.25);
|
||||
user-select: none;
|
||||
}
|
||||
|
||||
.theme-toggle:active {
|
||||
transform: translateY(1px);
|
||||
box-shadow: 0 4px 0 -3px rgba(0, 0, 0, 0.25);
|
||||
}
|
||||
|
||||
.theme-toggle__key {
|
||||
display: inline-flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
width: 36px;
|
||||
height: 28px;
|
||||
border-radius: 9px;
|
||||
background: var(--code-bg);
|
||||
color: var(--code-accent);
|
||||
border: 1px solid color-mix(in oklab, var(--code-accent) 30%, transparent);
|
||||
font-weight: 700;
|
||||
font-size: 12px;
|
||||
letter-spacing: 0.06em;
|
||||
text-shadow: 0 0 14px color-mix(in oklab, var(--code-accent) 55%, transparent);
|
||||
}
|
||||
|
||||
.theme-toggle__label {
|
||||
font-family: var(--font-pixel);
|
||||
letter-spacing: 0.12em;
|
||||
font-size: 12px;
|
||||
text-transform: uppercase;
|
||||
}
|
||||
|
||||
.theme-toggle:focus-visible {
|
||||
outline: 3px solid color-mix(in oklab, var(--accent2) 60%, transparent);
|
||||
outline-offset: 2px;
|
||||
}
|
||||
|
||||
.shell__nav {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: space-between;
|
||||
gap: 10px;
|
||||
padding: 10px 14px 12px;
|
||||
border-top: 1px solid color-mix(in oklab, var(--frame-border) 25%, transparent);
|
||||
background: linear-gradient(180deg, transparent, color-mix(in oklab, var(--panel2) 78%, transparent));
|
||||
}
|
||||
|
||||
.nav {
|
||||
display: flex;
|
||||
flex-wrap: wrap;
|
||||
gap: 12px;
|
||||
}
|
||||
|
||||
.nav__link {
|
||||
display: inline-flex;
|
||||
align-items: center;
|
||||
gap: 8px;
|
||||
padding: 6px 10px;
|
||||
border-radius: 999px;
|
||||
text-decoration: none;
|
||||
color: var(--text);
|
||||
background: color-mix(in oklab, var(--panel) 85%, transparent);
|
||||
border: 1px solid color-mix(in oklab, var(--frame-border) 20%, transparent);
|
||||
}
|
||||
|
||||
.nav__link:hover {
|
||||
border-color: color-mix(in oklab, var(--accent2) 45%, transparent);
|
||||
box-shadow: 0 0 0 2px color-mix(in oklab, var(--accent2) 30%, transparent);
|
||||
}
|
||||
|
||||
.nav__chev {
|
||||
color: var(--accent);
|
||||
font-weight: 700;
|
||||
}
|
||||
|
||||
.shell__status {
|
||||
display: inline-flex;
|
||||
align-items: center;
|
||||
gap: 10px;
|
||||
color: var(--muted);
|
||||
font-size: 12px;
|
||||
white-space: nowrap;
|
||||
}
|
||||
|
||||
.status__dot {
|
||||
width: 10px;
|
||||
height: 10px;
|
||||
border-radius: 999px;
|
||||
background: radial-gradient(circle at 30% 30%, var(--accent2), color-mix(in oklab, var(--accent2) 30%, #000));
|
||||
box-shadow: 0 0 0 2px color-mix(in oklab, var(--accent2) 18%, transparent), 0 0 18px color-mix(in oklab, var(--accent2) 50%, transparent);
|
||||
}
|
||||
|
||||
.content {
|
||||
padding: 18px 16px 48px;
|
||||
}
|
||||
|
||||
.terminal {
|
||||
position: relative;
|
||||
max-width: 1120px;
|
||||
margin: 0 auto;
|
||||
border-radius: var(--radius);
|
||||
border: var(--border) solid var(--frame-border);
|
||||
background: linear-gradient(180deg, color-mix(in oklab, var(--panel) 92%, transparent), color-mix(in oklab, var(--panel2) 86%, transparent));
|
||||
box-shadow: var(--shadow-px);
|
||||
padding: 18px 16px 16px;
|
||||
}
|
||||
|
||||
.terminal__prompt {
|
||||
display: block;
|
||||
padding: 10px 12px;
|
||||
border-radius: var(--radius-sm);
|
||||
background: var(--code-bg);
|
||||
color: var(--code-fg);
|
||||
border: 1px solid color-mix(in oklab, var(--frame-border) 18%, transparent);
|
||||
overflow-x: auto;
|
||||
white-space: nowrap;
|
||||
}
|
||||
|
||||
.prompt__user {
|
||||
color: var(--code-accent);
|
||||
text-shadow: 0 0 16px color-mix(in oklab, var(--code-accent) 52%, transparent);
|
||||
}
|
||||
|
||||
.prompt__host {
|
||||
color: color-mix(in oklab, var(--code-fg) 92%, var(--accent2));
|
||||
}
|
||||
|
||||
.prompt__path {
|
||||
color: color-mix(in oklab, var(--code-fg) 78%, var(--link));
|
||||
}
|
||||
|
||||
.prompt__cmd {
|
||||
margin-left: 8px;
|
||||
color: color-mix(in oklab, var(--code-fg) 90%, var(--accent));
|
||||
}
|
||||
|
||||
.terminal__summary {
|
||||
margin: 12px 2px 0;
|
||||
color: var(--muted);
|
||||
font-size: 14px;
|
||||
line-height: 1.5;
|
||||
}
|
||||
|
||||
.terminal__meta {
|
||||
margin: 12px 2px 0;
|
||||
padding: 12px 12px;
|
||||
border-radius: var(--radius-sm);
|
||||
border: 1px dashed color-mix(in oklab, var(--frame-border) 25%, transparent);
|
||||
background: color-mix(in oklab, var(--panel) 76%, transparent);
|
||||
color: var(--faint);
|
||||
font-size: 13px;
|
||||
}
|
||||
|
||||
.terminal__meta summary {
|
||||
cursor: pointer;
|
||||
font-family: var(--font-pixel);
|
||||
letter-spacing: 0.08em;
|
||||
text-transform: uppercase;
|
||||
color: var(--text);
|
||||
}
|
||||
|
||||
.terminal__meta ul {
|
||||
margin: 10px 0 0 18px;
|
||||
}
|
||||
|
||||
.terminal__footer {
|
||||
margin-top: 22px;
|
||||
padding-top: 16px;
|
||||
border-top: 1px solid color-mix(in oklab, var(--frame-border) 20%, transparent);
|
||||
color: var(--muted);
|
||||
font-size: 13px;
|
||||
}
|
||||
|
||||
.footer__actions {
|
||||
margin-top: 14px;
|
||||
display: flex;
|
||||
justify-content: flex-end;
|
||||
}
|
||||
|
||||
.terminal__footer a {
|
||||
color: var(--link);
|
||||
text-decoration: none;
|
||||
border-bottom: 1px dotted color-mix(in oklab, var(--link) 55%, transparent);
|
||||
}
|
||||
|
||||
.terminal__footer a:hover {
|
||||
color: var(--link2);
|
||||
border-bottom-color: color-mix(in oklab, var(--link2) 75%, transparent);
|
||||
}
|
||||
|
||||
.footer__hint {
|
||||
margin-top: 8px;
|
||||
color: var(--faint);
|
||||
}
|
||||
|
||||
kbd {
|
||||
font-family: var(--font-body);
|
||||
font-size: 0.9em;
|
||||
padding: 2px 6px;
|
||||
border-radius: 8px;
|
||||
border: 1px solid color-mix(in oklab, var(--frame-border) 18%, transparent);
|
||||
background: color-mix(in oklab, var(--panel) 65%, transparent);
|
||||
box-shadow: 0 6px 0 -4px rgba(0, 0, 0, 0.18);
|
||||
}
|
||||
|
||||
@supports not (color: color-mix(in oklab, black, white)) {
|
||||
body::before,
|
||||
body::after {
|
||||
opacity: 0.2;
|
||||
}
|
||||
}
|
||||
@@ -1,55 +0,0 @@
|
||||
const THEME_STORAGE_KEY = "openclaw:theme";
|
||||
|
||||
function safeGet(key) {
|
||||
try {
|
||||
return localStorage.getItem(key);
|
||||
} catch {
|
||||
return null;
|
||||
}
|
||||
}
|
||||
|
||||
function safeSet(key, value) {
|
||||
try {
|
||||
localStorage.setItem(key, value);
|
||||
} catch {
|
||||
// ignore
|
||||
}
|
||||
}
|
||||
|
||||
function preferredTheme() {
|
||||
const stored = safeGet(THEME_STORAGE_KEY);
|
||||
if (stored === "light" || stored === "dark") return stored;
|
||||
return window.matchMedia?.("(prefers-color-scheme: dark)").matches ? "dark" : "light";
|
||||
}
|
||||
|
||||
function applyTheme(theme) {
|
||||
document.documentElement.dataset.theme = theme;
|
||||
|
||||
const toggle = document.querySelector("[data-theme-toggle]");
|
||||
const label = document.querySelector("[data-theme-label]");
|
||||
|
||||
if (toggle instanceof HTMLButtonElement) toggle.setAttribute("aria-pressed", theme === "dark" ? "true" : "false");
|
||||
if (label) label.textContent = theme === "dark" ? "dark" : "light";
|
||||
}
|
||||
|
||||
function toggleTheme() {
|
||||
const current = document.documentElement.dataset.theme === "dark" ? "dark" : "light";
|
||||
const next = current === "dark" ? "light" : "dark";
|
||||
safeSet(THEME_STORAGE_KEY, next);
|
||||
applyTheme(next);
|
||||
}
|
||||
|
||||
applyTheme(preferredTheme());
|
||||
|
||||
document.addEventListener("click", (event) => {
|
||||
const target = event.target;
|
||||
const button = target instanceof Element ? target.closest("[data-theme-toggle]") : null;
|
||||
if (button) toggleTheme();
|
||||
});
|
||||
|
||||
document.addEventListener("keydown", (event) => {
|
||||
if (event.key === "F2") {
|
||||
event.preventDefault();
|
||||
toggleTheme();
|
||||
}
|
||||
});
|
||||
@@ -78,8 +78,8 @@ export AWS_BEARER_TOKEN_BEDROCK="..."
|
||||
auth: "aws-sdk",
|
||||
models: [
|
||||
{
|
||||
id: "anthropic.claude-opus-4-5-20251101-v1:0",
|
||||
name: "Claude Opus 4.5 (Bedrock)",
|
||||
id: "us.anthropic.claude-opus-4-6-v1:0",
|
||||
name: "Claude Opus 4.6 (Bedrock)",
|
||||
reasoning: true,
|
||||
input: ["text", "image"],
|
||||
cost: { input: 0, output: 0, cacheRead: 0, cacheWrite: 0 },
|
||||
@@ -92,7 +92,7 @@ export AWS_BEARER_TOKEN_BEDROCK="..."
|
||||
},
|
||||
agents: {
|
||||
defaults: {
|
||||
model: { primary: "amazon-bedrock/anthropic.claude-opus-4-5-20251101-v1:0" },
|
||||
model: { primary: "amazon-bedrock/us.anthropic.claude-opus-4-6-v1:0" },
|
||||
},
|
||||
},
|
||||
}
|
||||
|
||||
@@ -196,6 +196,7 @@ Notes:
|
||||
- If `channels` is present, any channel not listed is denied by default.
|
||||
- Use a `"*"` channel entry to apply defaults across all channels; explicit channel entries override the wildcard.
|
||||
- Threads inherit parent channel config (allowlist, `requireMention`, skills, prompts, etc.) unless you add the thread channel id explicitly.
|
||||
- Owner hint: when a per-guild or per-channel `users` allowlist matches the sender, OpenClaw treats that sender as the owner in the system prompt. For a global owner across channels, set `commands.ownerAllowFrom`.
|
||||
- Bot-authored messages are ignored by default; set `channels.discord.allowBots=true` to allow them (own messages remain filtered).
|
||||
- Warning: If you allow replies to other bots (`channels.discord.allowBots=true`), prevent bot-to-bot reply loops with `requireMention`, `channels.discord.guilds.*.channels.<id>.users` allowlists, and/or clear guardrails in `AGENTS.md` and `SOUL.md`.
|
||||
|
||||
@@ -334,7 +335,7 @@ ack reaction after the bot replies.
|
||||
- `guilds.<id>.channels.<channel>.toolsBySender`: optional per-sender tool policy overrides within the channel (`"*"` wildcard supported).
|
||||
- `guilds.<id>.channels.<channel>.users`: optional per-channel user allowlist.
|
||||
- `guilds.<id>.channels.<channel>.skills`: skill filter (omit = all skills, empty = none).
|
||||
- `guilds.<id>.channels.<channel>.systemPrompt`: extra system prompt for the channel (combined with channel topic).
|
||||
- `guilds.<id>.channels.<channel>.systemPrompt`: extra system prompt for the channel. Discord channel topics are injected as **untrusted** context (not system prompt).
|
||||
- `guilds.<id>.channels.<channel>.enabled`: set `false` to disable the channel.
|
||||
- `guilds.<id>.channels`: channel rules (keys are channel slugs or ids).
|
||||
- `guilds.<id>.requireMention`: per-guild mention requirement (overridable per channel).
|
||||
|
||||
@@ -447,7 +447,75 @@ openclaw pairing list feishu
|
||||
|
||||
### Streaming
|
||||
|
||||
Feishu does not support message editing, so block streaming is enabled by default (`blockStreaming: true`). The bot waits for the full reply before sending.
|
||||
Feishu supports streaming replies via interactive cards. When enabled, the bot updates a card as it generates text.
|
||||
|
||||
```json5
|
||||
{
|
||||
channels: {
|
||||
feishu: {
|
||||
streaming: true, // enable streaming card output (default true)
|
||||
blockStreaming: true, // enable block-level streaming (default true)
|
||||
},
|
||||
},
|
||||
}
|
||||
```
|
||||
|
||||
Set `streaming: false` to wait for the full reply before sending.
|
||||
|
||||
### Multi-agent routing
|
||||
|
||||
Use `bindings` to route Feishu DMs or groups to different agents.
|
||||
|
||||
```json5
|
||||
{
|
||||
agents: {
|
||||
list: [
|
||||
{ id: "main" },
|
||||
{
|
||||
id: "clawd-fan",
|
||||
workspace: "/home/user/clawd-fan",
|
||||
agentDir: "/home/user/.openclaw/agents/clawd-fan/agent",
|
||||
},
|
||||
{
|
||||
id: "clawd-xi",
|
||||
workspace: "/home/user/clawd-xi",
|
||||
agentDir: "/home/user/.openclaw/agents/clawd-xi/agent",
|
||||
},
|
||||
],
|
||||
},
|
||||
bindings: [
|
||||
{
|
||||
agentId: "main",
|
||||
match: {
|
||||
channel: "feishu",
|
||||
peer: { kind: "dm", id: "ou_xxx" },
|
||||
},
|
||||
},
|
||||
{
|
||||
agentId: "clawd-fan",
|
||||
match: {
|
||||
channel: "feishu",
|
||||
peer: { kind: "dm", id: "ou_yyy" },
|
||||
},
|
||||
},
|
||||
{
|
||||
agentId: "clawd-xi",
|
||||
match: {
|
||||
channel: "feishu",
|
||||
peer: { kind: "group", id: "oc_zzz" },
|
||||
},
|
||||
},
|
||||
],
|
||||
}
|
||||
```
|
||||
|
||||
Routing fields:
|
||||
|
||||
- `match.channel`: `"feishu"`
|
||||
- `match.peer.kind`: `"dm"` or `"group"`
|
||||
- `match.peer.id`: user Open ID (`ou_xxx`) or group ID (`oc_xxx`)
|
||||
|
||||
See [Get group/user IDs](#get-groupuser-ids) for lookup tips.
|
||||
|
||||
---
|
||||
|
||||
@@ -472,7 +540,8 @@ Key options:
|
||||
| `channels.feishu.groups.<chat_id>.enabled` | Enable group | `true` |
|
||||
| `channels.feishu.textChunkLimit` | Message chunk size | `2000` |
|
||||
| `channels.feishu.mediaMaxMb` | Media size limit | `30` |
|
||||
| `channels.feishu.blockStreaming` | Disable streaming | `true` |
|
||||
| `channels.feishu.streaming` | Enable streaming card output | `true` |
|
||||
| `channels.feishu.blockStreaming` | Enable block streaming | `true` |
|
||||
|
||||
---
|
||||
|
||||
@@ -492,6 +561,7 @@ Key options:
|
||||
### Receive
|
||||
|
||||
- ✅ Text
|
||||
- ✅ Rich text (post)
|
||||
- ✅ Images
|
||||
- ✅ Files
|
||||
- ✅ Audio
|
||||
|
||||
@@ -392,6 +392,23 @@ Two independent controls:
|
||||
|
||||
Most users want: `groupPolicy: "allowlist"` + `groupAllowFrom` + specific groups listed in `channels.telegram.groups`
|
||||
|
||||
To allow **any group member** to talk in a specific group (while still keeping control commands restricted to authorized senders), set a per-group override:
|
||||
|
||||
```json5
|
||||
{
|
||||
channels: {
|
||||
telegram: {
|
||||
groups: {
|
||||
"-1001234567890": {
|
||||
groupPolicy: "open",
|
||||
requireMention: false,
|
||||
},
|
||||
},
|
||||
},
|
||||
},
|
||||
}
|
||||
```
|
||||
|
||||
## Long-polling vs webhook
|
||||
|
||||
- Default: long-polling (no public URL required).
|
||||
@@ -714,12 +731,14 @@ Provider options:
|
||||
- `channels.telegram.groupPolicy`: `open | allowlist | disabled` (default: allowlist).
|
||||
- `channels.telegram.groupAllowFrom`: group sender allowlist (ids/usernames).
|
||||
- `channels.telegram.groups`: per-group defaults + allowlist (use `"*"` for global defaults).
|
||||
- `channels.telegram.groups.<id>.groupPolicy`: per-group override for groupPolicy (`open | allowlist | disabled`).
|
||||
- `channels.telegram.groups.<id>.requireMention`: mention gating default.
|
||||
- `channels.telegram.groups.<id>.skills`: skill filter (omit = all skills, empty = none).
|
||||
- `channels.telegram.groups.<id>.allowFrom`: per-group sender allowlist override.
|
||||
- `channels.telegram.groups.<id>.systemPrompt`: extra system prompt for the group.
|
||||
- `channels.telegram.groups.<id>.enabled`: disable the group when `false`.
|
||||
- `channels.telegram.groups.<id>.topics.<threadId>.*`: per-topic overrides (same fields as group).
|
||||
- `channels.telegram.groups.<id>.topics.<threadId>.groupPolicy`: per-topic override for groupPolicy (`open | allowlist | disabled`).
|
||||
- `channels.telegram.groups.<id>.topics.<threadId>.requireMention`: per-topic mention gating override.
|
||||
- `channels.telegram.capabilities.inlineButtons`: `off | dm | group | all | allowlist` (default: allowlist).
|
||||
- `channels.telegram.accounts.<account>.capabilities.inlineButtons`: per-account override.
|
||||
|
||||
@@ -61,6 +61,9 @@ openclaw devices revoke --device <deviceId> --role node
|
||||
- `--timeout <ms>`: RPC timeout.
|
||||
- `--json`: JSON output (recommended for scripting).
|
||||
|
||||
Note: when you set `--url`, the CLI does not fall back to config or environment credentials.
|
||||
Pass `--token` or `--password` explicitly. Missing explicit credentials is an error.
|
||||
|
||||
## Notes
|
||||
|
||||
- Token rotation returns a new token (sensitive). Treat it like a secret.
|
||||
|
||||
@@ -78,6 +78,9 @@ Shared options (where supported):
|
||||
- `--timeout <ms>`: timeout/budget (varies per command).
|
||||
- `--expect-final`: wait for a “final” response (agent calls).
|
||||
|
||||
Note: when you set `--url`, the CLI does not fall back to config or environment credentials.
|
||||
Pass `--token` or `--password` explicitly. Missing explicit credentials is an error.
|
||||
|
||||
### `gateway health`
|
||||
|
||||
```bash
|
||||
|
||||
@@ -715,6 +715,8 @@ openclaw logs --no-color
|
||||
### `gateway <subcommand>`
|
||||
|
||||
Gateway CLI helpers (use `--url`, `--token`, `--password`, `--timeout`, `--expect-final` for RPC subcommands).
|
||||
When you pass `--url`, the CLI does not auto-apply config or environment credentials.
|
||||
Include `--token` or `--password` explicitly. Missing explicit credentials is an error.
|
||||
|
||||
Subcommands:
|
||||
|
||||
|
||||
@@ -9,9 +9,12 @@ title: "onboard"
|
||||
|
||||
Interactive onboarding wizard (local or remote Gateway setup).
|
||||
|
||||
Related:
|
||||
## Related guides
|
||||
|
||||
- Wizard guide: [Onboarding](/start/onboarding)
|
||||
- CLI onboarding hub: [Onboarding Wizard (CLI)](/start/wizard)
|
||||
- CLI onboarding reference: [CLI Onboarding Reference](/start/wizard-cli-reference)
|
||||
- CLI automation: [CLI Automation](/start/wizard-cli-automation)
|
||||
- macOS onboarding: [Onboarding (macOS App)](/start/onboarding)
|
||||
|
||||
## Examples
|
||||
|
||||
@@ -27,3 +30,14 @@ Flow notes:
|
||||
- `quickstart`: minimal prompts, auto-generates a gateway token.
|
||||
- `manual`: full prompts for port/bind/auth (alias of `advanced`).
|
||||
- Fastest first chat: `openclaw dashboard` (Control UI, no channel setup).
|
||||
|
||||
## Common follow-up commands
|
||||
|
||||
```bash
|
||||
openclaw configure
|
||||
openclaw agents add <name>
|
||||
```
|
||||
|
||||
<Note>
|
||||
`--json` does not imply non-interactive mode. Use `--non-interactive` for scripts.
|
||||
</Note>
|
||||
|
||||
53
docs/concepts/features.md
Normal file
53
docs/concepts/features.md
Normal file
@@ -0,0 +1,53 @@
|
||||
---
|
||||
summary: "OpenClaw capabilities across channels, routing, media, and UX."
|
||||
read_when:
|
||||
- You want a full list of what OpenClaw supports
|
||||
title: "Features"
|
||||
---
|
||||
|
||||
## Highlights
|
||||
|
||||
<Columns>
|
||||
<Card title="Channels" icon="message-square">
|
||||
WhatsApp, Telegram, Discord, and iMessage with a single Gateway.
|
||||
</Card>
|
||||
<Card title="Plugins" icon="plug">
|
||||
Add Mattermost and more with extensions.
|
||||
</Card>
|
||||
<Card title="Routing" icon="route">
|
||||
Multi-agent routing with isolated sessions.
|
||||
</Card>
|
||||
<Card title="Media" icon="image">
|
||||
Images, audio, and documents in and out.
|
||||
</Card>
|
||||
<Card title="Apps and UI" icon="monitor">
|
||||
Web Control UI and macOS companion app.
|
||||
</Card>
|
||||
<Card title="Mobile nodes" icon="smartphone">
|
||||
iOS and Android nodes with Canvas support.
|
||||
</Card>
|
||||
</Columns>
|
||||
|
||||
## Full list
|
||||
|
||||
- WhatsApp integration via WhatsApp Web (Baileys)
|
||||
- Telegram bot support (grammY)
|
||||
- Discord bot support (channels.discord.js)
|
||||
- Mattermost bot support (plugin)
|
||||
- iMessage integration via local imsg CLI (macOS)
|
||||
- Agent bridge for Pi in RPC mode with tool streaming
|
||||
- Streaming and chunking for long responses
|
||||
- Multi-agent routing for isolated sessions per workspace or sender
|
||||
- Subscription auth for Anthropic and OpenAI via OAuth
|
||||
- Sessions: direct chats collapse into shared `main`; groups are isolated
|
||||
- Group chat support with mention based activation
|
||||
- Media support for images, audio, and documents
|
||||
- Optional voice note transcription hook
|
||||
- WebChat and macOS menu bar app
|
||||
- iOS node with pairing and Canvas surface
|
||||
- Android node with pairing, Canvas, chat, and camera
|
||||
|
||||
<Note>
|
||||
Legacy Claude, Codex, Gemini, and Opencode paths have been removed. Pi is the only
|
||||
coding agent path.
|
||||
</Note>
|
||||
@@ -148,7 +148,7 @@ Details: [Thinking + reasoning directives](/tools/thinking) and [Token use](/tok
|
||||
|
||||
Outbound message formatting is centralized in `messages`:
|
||||
|
||||
- `messages.responsePrefix` (outbound prefix) and `channels.whatsapp.messagePrefix` (WhatsApp inbound prefix)
|
||||
- `messages.responsePrefix`, `channels.<channel>.responsePrefix`, and `channels.<channel>.accounts.<id>.responsePrefix` (outbound prefix cascade), plus `channels.whatsapp.messagePrefix` (WhatsApp inbound prefix)
|
||||
- Reply threading via `replyToMode` and per-channel defaults
|
||||
|
||||
Details: [Configuration](/gateway/configuration#messages) and channel docs.
|
||||
|
||||
@@ -13,7 +13,7 @@ For model selection rules, see [/concepts/models](/concepts/models).
|
||||
|
||||
## Quick rules
|
||||
|
||||
- Model refs use `provider/model` (example: `opencode/claude-opus-4-5`).
|
||||
- Model refs use `provider/model` (example: `opencode/claude-opus-4-6`).
|
||||
- If you set `agents.defaults.models`, it becomes the allowlist.
|
||||
- CLI helpers: `openclaw onboard`, `openclaw models list`, `openclaw models set <provider/model>`.
|
||||
|
||||
@@ -26,12 +26,12 @@ OpenClaw ships with the pi‑ai catalog. These providers require **no**
|
||||
|
||||
- Provider: `openai`
|
||||
- Auth: `OPENAI_API_KEY`
|
||||
- Example model: `openai/gpt-5.2`
|
||||
- Example model: `openai/gpt-5.1-codex`
|
||||
- CLI: `openclaw onboard --auth-choice openai-api-key`
|
||||
|
||||
```json5
|
||||
{
|
||||
agents: { defaults: { model: { primary: "openai/gpt-5.2" } } },
|
||||
agents: { defaults: { model: { primary: "openai/gpt-5.1-codex" } } },
|
||||
}
|
||||
```
|
||||
|
||||
@@ -39,12 +39,12 @@ OpenClaw ships with the pi‑ai catalog. These providers require **no**
|
||||
|
||||
- Provider: `anthropic`
|
||||
- Auth: `ANTHROPIC_API_KEY` or `claude setup-token`
|
||||
- Example model: `anthropic/claude-opus-4-5`
|
||||
- Example model: `anthropic/claude-opus-4-6`
|
||||
- CLI: `openclaw onboard --auth-choice token` (paste setup-token) or `openclaw models auth paste-token --provider anthropic`
|
||||
|
||||
```json5
|
||||
{
|
||||
agents: { defaults: { model: { primary: "anthropic/claude-opus-4-5" } } },
|
||||
agents: { defaults: { model: { primary: "anthropic/claude-opus-4-6" } } },
|
||||
}
|
||||
```
|
||||
|
||||
@@ -52,12 +52,12 @@ OpenClaw ships with the pi‑ai catalog. These providers require **no**
|
||||
|
||||
- Provider: `openai-codex`
|
||||
- Auth: OAuth (ChatGPT)
|
||||
- Example model: `openai-codex/gpt-5.2`
|
||||
- Example model: `openai-codex/gpt-5.3-codex`
|
||||
- CLI: `openclaw onboard --auth-choice openai-codex` or `openclaw models auth login --provider openai-codex`
|
||||
|
||||
```json5
|
||||
{
|
||||
agents: { defaults: { model: { primary: "openai-codex/gpt-5.2" } } },
|
||||
agents: { defaults: { model: { primary: "openai-codex/gpt-5.3-codex" } } },
|
||||
}
|
||||
```
|
||||
|
||||
@@ -65,12 +65,12 @@ OpenClaw ships with the pi‑ai catalog. These providers require **no**
|
||||
|
||||
- Provider: `opencode`
|
||||
- Auth: `OPENCODE_API_KEY` (or `OPENCODE_ZEN_API_KEY`)
|
||||
- Example model: `opencode/claude-opus-4-5`
|
||||
- Example model: `opencode/claude-opus-4-6`
|
||||
- CLI: `openclaw onboard --auth-choice opencode-zen`
|
||||
|
||||
```json5
|
||||
{
|
||||
agents: { defaults: { model: { primary: "opencode/claude-opus-4-5" } } },
|
||||
agents: { defaults: { model: { primary: "opencode/claude-opus-4-6" } } },
|
||||
}
|
||||
```
|
||||
|
||||
@@ -106,7 +106,7 @@ OpenClaw ships with the pi‑ai catalog. These providers require **no**
|
||||
|
||||
- Provider: `vercel-ai-gateway`
|
||||
- Auth: `AI_GATEWAY_API_KEY`
|
||||
- Example model: `vercel-ai-gateway/anthropic/claude-opus-4.5`
|
||||
- Example model: `vercel-ai-gateway/anthropic/claude-opus-4.6`
|
||||
- CLI: `openclaw onboard --auth-choice ai-gateway-api-key`
|
||||
|
||||
### Other built-in providers
|
||||
@@ -309,7 +309,7 @@ Notes:
|
||||
|
||||
```bash
|
||||
openclaw onboard --auth-choice opencode-zen
|
||||
openclaw models set opencode/claude-opus-4-5
|
||||
openclaw models set opencode/claude-opus-4-6
|
||||
openclaw models list
|
||||
```
|
||||
|
||||
|
||||
@@ -83,7 +83,7 @@ Example allowlist config:
|
||||
model: { primary: "anthropic/claude-sonnet-4-5" },
|
||||
models: {
|
||||
"anthropic/claude-sonnet-4-5": { alias: "Sonnet" },
|
||||
"anthropic/claude-opus-4-5": { alias: "Opus" },
|
||||
"anthropic/claude-opus-4-6": { alias: "Opus" },
|
||||
},
|
||||
},
|
||||
}
|
||||
|
||||
@@ -221,7 +221,7 @@ Split by channel: route WhatsApp to a fast everyday agent and Telegram to an Opu
|
||||
id: "opus",
|
||||
name: "Deep Work",
|
||||
workspace: "~/.openclaw/workspace-opus",
|
||||
model: "anthropic/claude-opus-4-5",
|
||||
model: "anthropic/claude-opus-4-6",
|
||||
},
|
||||
],
|
||||
},
|
||||
@@ -255,7 +255,7 @@ Keep WhatsApp on the fast agent, but route one DM to Opus:
|
||||
id: "opus",
|
||||
name: "Deep Work",
|
||||
workspace: "~/.openclaw/workspace-opus",
|
||||
model: "anthropic/claude-opus-4-5",
|
||||
model: "anthropic/claude-opus-4-6",
|
||||
},
|
||||
],
|
||||
},
|
||||
|
||||
@@ -17,9 +17,17 @@ Use `session.dmScope` to control how **direct messages** are grouped:
|
||||
- `per-account-channel-peer`: isolate by account + channel + sender (recommended for multi-account inboxes).
|
||||
Use `session.identityLinks` to map provider-prefixed peer ids to a canonical identity so the same person shares a DM session across channels when using `per-peer`, `per-channel-peer`, or `per-account-channel-peer`.
|
||||
|
||||
### Secure DM mode (recommended)
|
||||
### Secure DM mode (recommended for multi-user setups)
|
||||
|
||||
If your agent can receive DMs from **multiple people** (pairing approvals for more than one sender, a DM allowlist with multiple entries, or `dmPolicy: "open"`), enable **secure DM mode** to avoid cross-user context leakage:
|
||||
> **Security Warning:** If your agent can receive DMs from **multiple people**, you should strongly consider enabling secure DM mode. Without it, all users share the same conversation context, which can leak private information between users.
|
||||
|
||||
**Example of the problem with default settings:**
|
||||
|
||||
- Alice (`<SENDER_A>`) messages your agent about a private topic (for example, a medical appointment)
|
||||
- Bob (`<SENDER_B>`) messages your agent asking "What were we talking about?"
|
||||
- Because both DMs share the same session, the model may answer Bob using Alice's prior context.
|
||||
|
||||
**The fix:** Set `dmScope` to isolate sessions per user:
|
||||
|
||||
```json5
|
||||
// ~/.openclaw/openclaw.json
|
||||
@@ -31,11 +39,19 @@ If your agent can receive DMs from **multiple people** (pairing approvals for mo
|
||||
}
|
||||
```
|
||||
|
||||
**When to enable this:**
|
||||
|
||||
- You have pairing approvals for more than one sender
|
||||
- You use a DM allowlist with multiple entries
|
||||
- You set `dmPolicy: "open"`
|
||||
- Multiple phone numbers or accounts can message your agent
|
||||
|
||||
Notes:
|
||||
|
||||
- Default is `dmScope: "main"` for continuity (all DMs share the main session).
|
||||
- Default is `dmScope: "main"` for continuity (all DMs share the main session). This is fine for single-user setups.
|
||||
- For multi-account inboxes on the same channel, prefer `per-account-channel-peer`.
|
||||
- If the same person contacts you on multiple channels, use `session.identityLinks` to collapse their DM sessions into one canonical identity.
|
||||
- You can verify your DM settings with `openclaw security audit` (see [security](/cli/security)).
|
||||
|
||||
## Gateway is the source of truth
|
||||
|
||||
|
||||
599
docs/docs.json
599
docs/docs.json
@@ -2,28 +2,41 @@
|
||||
"$schema": "https://mintlify.com/docs.json",
|
||||
"name": "OpenClaw",
|
||||
"theme": "mint",
|
||||
"icons": {
|
||||
"library": "lucide"
|
||||
},
|
||||
"logo": {
|
||||
"light": "/assets/pixel-lobster.svg",
|
||||
"dark": "/assets/pixel-lobster.svg"
|
||||
},
|
||||
"fonts": {
|
||||
"body": {
|
||||
"family": "Fragment Mono"
|
||||
},
|
||||
"heading": {
|
||||
"family": "DM Sans"
|
||||
}
|
||||
},
|
||||
"favicon": "/assets/pixel-lobster.svg",
|
||||
"colors": {
|
||||
"primary": "#FF5A36"
|
||||
"primary": "#FF5A36",
|
||||
"dark": "#FF5A36",
|
||||
"light": "#FF8A6B"
|
||||
},
|
||||
"navbar": {
|
||||
"links": [
|
||||
{
|
||||
"label": "GitHub",
|
||||
"href": "https://github.com/openclaw/openclaw",
|
||||
"icon": "github"
|
||||
},
|
||||
{
|
||||
"label": "Releases",
|
||||
"href": "https://github.com/openclaw/openclaw/releases",
|
||||
"icon": "package"
|
||||
}
|
||||
]
|
||||
},
|
||||
"topbarLinks": [
|
||||
{
|
||||
"name": "中文",
|
||||
"url": "/zh-CN"
|
||||
},
|
||||
{
|
||||
"name": "GitHub",
|
||||
"url": "https://github.com/openclaw/openclaw"
|
||||
},
|
||||
{
|
||||
"name": "Releases",
|
||||
"url": "https://github.com/openclaw/openclaw/releases"
|
||||
}
|
||||
],
|
||||
"redirects": [
|
||||
{
|
||||
"source": "/cron",
|
||||
@@ -321,6 +334,14 @@
|
||||
"source": "/getting-started",
|
||||
"destination": "/start/getting-started"
|
||||
},
|
||||
{
|
||||
"source": "/quickstart",
|
||||
"destination": "/start/getting-started"
|
||||
},
|
||||
{
|
||||
"source": "/start/quickstart",
|
||||
"destination": "/start/getting-started"
|
||||
},
|
||||
{
|
||||
"source": "/gmail-pubsub",
|
||||
"destination": "/automation/gmail-pubsub"
|
||||
@@ -677,6 +698,18 @@
|
||||
"source": "/wizard",
|
||||
"destination": "/start/wizard"
|
||||
},
|
||||
{
|
||||
"source": "/start/wizard-cli-flow",
|
||||
"destination": "/start/wizard-cli-reference"
|
||||
},
|
||||
{
|
||||
"source": "/start/wizard-cli-auth",
|
||||
"destination": "/start/wizard-cli-reference"
|
||||
},
|
||||
{
|
||||
"source": "/start/wizard-cli-outputs",
|
||||
"destination": "/start/wizard-cli-reference"
|
||||
},
|
||||
{
|
||||
"source": "/start/faq",
|
||||
"destination": "/help/faq"
|
||||
@@ -690,20 +723,52 @@
|
||||
"destination": "/plugin"
|
||||
},
|
||||
{
|
||||
"source": "/install/railway",
|
||||
"destination": "/railway"
|
||||
"source": "/railway",
|
||||
"destination": "/install/railway"
|
||||
},
|
||||
{
|
||||
"source": "/install/northflank",
|
||||
"destination": "/northflank"
|
||||
"source": "/northflank",
|
||||
"destination": "/install/northflank"
|
||||
},
|
||||
{
|
||||
"source": "/install/northflank/",
|
||||
"destination": "/northflank"
|
||||
"source": "/render",
|
||||
"destination": "/install/render"
|
||||
},
|
||||
{
|
||||
"source": "/gcp",
|
||||
"destination": "/platforms/gcp"
|
||||
"destination": "/install/gcp"
|
||||
},
|
||||
{
|
||||
"source": "/platforms/fly",
|
||||
"destination": "/install/fly"
|
||||
},
|
||||
{
|
||||
"source": "/platforms/hetzner",
|
||||
"destination": "/install/hetzner"
|
||||
},
|
||||
{
|
||||
"source": "/platforms/gcp",
|
||||
"destination": "/install/gcp"
|
||||
},
|
||||
{
|
||||
"source": "/platforms/macos-vm",
|
||||
"destination": "/install/macos-vm"
|
||||
},
|
||||
{
|
||||
"source": "/platforms/exe-dev",
|
||||
"destination": "/install/exe-dev"
|
||||
},
|
||||
{
|
||||
"source": "/platforms/railway",
|
||||
"destination": "/install/railway"
|
||||
},
|
||||
{
|
||||
"source": "/platforms/render",
|
||||
"destination": "/install/render"
|
||||
},
|
||||
{
|
||||
"source": "/platforms/northflank",
|
||||
"destination": "/install/northflank"
|
||||
}
|
||||
],
|
||||
"navigation": {
|
||||
@@ -716,44 +781,55 @@
|
||||
"groups": [
|
||||
{
|
||||
"group": "Overview",
|
||||
"pages": ["index", "start/showcase", "start/lore"]
|
||||
"pages": ["index", "concepts/features", "start/showcase"]
|
||||
},
|
||||
{
|
||||
"group": "Installation",
|
||||
"group": "First steps",
|
||||
"pages": ["start/getting-started", "start/wizard", "start/onboarding"]
|
||||
},
|
||||
{
|
||||
"group": "Guides",
|
||||
"pages": ["start/openclaw"]
|
||||
}
|
||||
]
|
||||
},
|
||||
{
|
||||
"tab": "Install",
|
||||
"groups": [
|
||||
{
|
||||
"group": "Install overview",
|
||||
"pages": ["install/index", "install/installer"]
|
||||
},
|
||||
{
|
||||
"group": "Install methods",
|
||||
"pages": [
|
||||
"install/index",
|
||||
"install/installer",
|
||||
"install/node",
|
||||
"install/docker",
|
||||
"install/bun",
|
||||
"install/nix",
|
||||
"install/ansible",
|
||||
"install/development-channels",
|
||||
"install/updating",
|
||||
"install/uninstall"
|
||||
"install/bun"
|
||||
]
|
||||
},
|
||||
{
|
||||
"group": "Setup",
|
||||
"group": "Maintenance",
|
||||
"pages": ["install/updating", "install/migrating", "install/uninstall"]
|
||||
},
|
||||
{
|
||||
"group": "Hosting and deployment",
|
||||
"pages": [
|
||||
"start/getting-started",
|
||||
"start/wizard",
|
||||
"start/setup",
|
||||
"start/onboarding",
|
||||
"start/pairing",
|
||||
"start/openclaw",
|
||||
"start/hubs"
|
||||
"install/fly",
|
||||
"install/hetzner",
|
||||
"install/gcp",
|
||||
"install/macos-vm",
|
||||
"install/exe-dev",
|
||||
"install/railway",
|
||||
"install/render",
|
||||
"install/northflank"
|
||||
]
|
||||
},
|
||||
{
|
||||
"group": "Platforms",
|
||||
"pages": [
|
||||
"platforms/index",
|
||||
"platforms/macos",
|
||||
"platforms/linux",
|
||||
"platforms/windows",
|
||||
"platforms/android",
|
||||
"platforms/ios"
|
||||
]
|
||||
"group": "Advanced",
|
||||
"pages": ["install/development-channels"]
|
||||
}
|
||||
]
|
||||
},
|
||||
@@ -787,6 +863,7 @@
|
||||
{
|
||||
"group": "Configuration",
|
||||
"pages": [
|
||||
"start/pairing",
|
||||
"concepts/group-messages",
|
||||
"concepts/groups",
|
||||
"broadcast-groups",
|
||||
@@ -809,6 +886,7 @@
|
||||
"concepts/system-prompt",
|
||||
"concepts/context",
|
||||
"concepts/agent-workspace",
|
||||
"start/bootstrapping",
|
||||
"concepts/oauth"
|
||||
]
|
||||
},
|
||||
@@ -940,7 +1018,46 @@
|
||||
]
|
||||
},
|
||||
{
|
||||
"tab": "Infrastructure",
|
||||
"tab": "Platforms",
|
||||
"groups": [
|
||||
{
|
||||
"group": "Platforms overview",
|
||||
"pages": [
|
||||
"platforms/index",
|
||||
"platforms/macos",
|
||||
"platforms/linux",
|
||||
"platforms/windows",
|
||||
"platforms/android",
|
||||
"platforms/ios"
|
||||
]
|
||||
},
|
||||
{
|
||||
"group": "macOS companion app",
|
||||
"pages": [
|
||||
"platforms/mac/dev-setup",
|
||||
"platforms/mac/menu-bar",
|
||||
"platforms/mac/voicewake",
|
||||
"platforms/mac/voice-overlay",
|
||||
"platforms/mac/webchat",
|
||||
"platforms/mac/canvas",
|
||||
"platforms/mac/child-process",
|
||||
"platforms/mac/health",
|
||||
"platforms/mac/icon",
|
||||
"platforms/mac/logging",
|
||||
"platforms/mac/permissions",
|
||||
"platforms/mac/remote",
|
||||
"platforms/mac/signing",
|
||||
"platforms/mac/release",
|
||||
"platforms/mac/bundled-gateway",
|
||||
"platforms/mac/xpc",
|
||||
"platforms/mac/skills",
|
||||
"platforms/mac/peekaboo"
|
||||
]
|
||||
}
|
||||
]
|
||||
},
|
||||
{
|
||||
"tab": "Gateway & Ops",
|
||||
"groups": [
|
||||
{
|
||||
"group": "Gateway",
|
||||
@@ -983,25 +1100,18 @@
|
||||
},
|
||||
{
|
||||
"group": "Networking and discovery",
|
||||
"pages": ["gateway/pairing", "gateway/discovery", "gateway/bonjour"]
|
||||
"pages": [
|
||||
"gateway/network-model",
|
||||
"gateway/pairing",
|
||||
"gateway/discovery",
|
||||
"gateway/bonjour"
|
||||
]
|
||||
}
|
||||
]
|
||||
},
|
||||
{
|
||||
"group": "Remote access and deployment",
|
||||
"pages": [
|
||||
"gateway/remote",
|
||||
"gateway/remote-gateway-readme",
|
||||
"gateway/tailscale",
|
||||
"platforms/fly",
|
||||
"platforms/hetzner",
|
||||
"platforms/gcp",
|
||||
"platforms/macos-vm",
|
||||
"platforms/exe-dev",
|
||||
"railway",
|
||||
"render",
|
||||
"northflank"
|
||||
]
|
||||
"group": "Remote access",
|
||||
"pages": ["gateway/remote", "gateway/remote-gateway-readme", "gateway/tailscale"]
|
||||
},
|
||||
{
|
||||
"group": "Security",
|
||||
@@ -1010,29 +1120,6 @@
|
||||
{
|
||||
"group": "Web interfaces",
|
||||
"pages": ["web/index", "web/control-ui", "web/dashboard", "web/webchat", "tui"]
|
||||
},
|
||||
{
|
||||
"group": "macOS companion app",
|
||||
"pages": [
|
||||
"platforms/mac/dev-setup",
|
||||
"platforms/mac/menu-bar",
|
||||
"platforms/mac/voicewake",
|
||||
"platforms/mac/voice-overlay",
|
||||
"platforms/mac/webchat",
|
||||
"platforms/mac/canvas",
|
||||
"platforms/mac/child-process",
|
||||
"platforms/mac/health",
|
||||
"platforms/mac/icon",
|
||||
"platforms/mac/logging",
|
||||
"platforms/mac/permissions",
|
||||
"platforms/mac/remote",
|
||||
"platforms/mac/signing",
|
||||
"platforms/mac/release",
|
||||
"platforms/mac/bundled-gateway",
|
||||
"platforms/mac/xpc",
|
||||
"platforms/mac/skills",
|
||||
"platforms/mac/peekaboo"
|
||||
]
|
||||
}
|
||||
]
|
||||
},
|
||||
@@ -1101,6 +1188,7 @@
|
||||
{
|
||||
"group": "Technical reference",
|
||||
"pages": [
|
||||
"reference/wizard",
|
||||
"concepts/typebox",
|
||||
"concepts/markdown-formatting",
|
||||
"concepts/typing-indicators",
|
||||
@@ -1109,6 +1197,10 @@
|
||||
"token-use"
|
||||
]
|
||||
},
|
||||
{
|
||||
"group": "Project",
|
||||
"pages": ["reference/credits"]
|
||||
},
|
||||
{
|
||||
"group": "Release notes",
|
||||
"pages": ["reference/RELEASING", "reference/test"]
|
||||
@@ -1122,6 +1214,10 @@
|
||||
"group": "Help",
|
||||
"pages": ["help/index", "help/troubleshooting", "help/faq"]
|
||||
},
|
||||
{
|
||||
"group": "Community",
|
||||
"pages": ["start/lore"]
|
||||
},
|
||||
{
|
||||
"group": "Environment and debugging",
|
||||
"pages": [
|
||||
@@ -1131,6 +1227,14 @@
|
||||
"scripts",
|
||||
"reference/session-management-compaction"
|
||||
]
|
||||
},
|
||||
{
|
||||
"group": "Developer workflows",
|
||||
"pages": ["start/setup"]
|
||||
},
|
||||
{
|
||||
"group": "Docs meta",
|
||||
"pages": ["start/hubs", "start/docs-directory"]
|
||||
}
|
||||
]
|
||||
}
|
||||
@@ -1140,60 +1244,79 @@
|
||||
"language": "zh-Hans",
|
||||
"tabs": [
|
||||
{
|
||||
"tab": "Get started",
|
||||
"tab": "快速开始",
|
||||
"groups": [
|
||||
{
|
||||
"group": "Overview",
|
||||
"pages": ["zh-CN/index", "zh-CN/start/showcase", "zh-CN/start/lore"]
|
||||
"group": "概览",
|
||||
"pages": ["zh-CN/index", "zh-CN/concepts/features", "zh-CN/start/showcase"]
|
||||
},
|
||||
{
|
||||
"group": "Installation",
|
||||
"pages": [
|
||||
"zh-CN/install/index",
|
||||
"zh-CN/install/installer",
|
||||
"zh-CN/install/docker",
|
||||
"zh-CN/install/bun",
|
||||
"zh-CN/install/nix",
|
||||
"zh-CN/install/ansible",
|
||||
"zh-CN/install/development-channels",
|
||||
"zh-CN/install/updating",
|
||||
"zh-CN/install/uninstall"
|
||||
]
|
||||
},
|
||||
{
|
||||
"group": "Setup",
|
||||
"group": "第一步",
|
||||
"pages": [
|
||||
"zh-CN/start/getting-started",
|
||||
"zh-CN/start/wizard",
|
||||
"zh-CN/start/setup",
|
||||
"zh-CN/start/onboarding",
|
||||
"zh-CN/start/pairing",
|
||||
"zh-CN/start/openclaw",
|
||||
"zh-CN/start/hubs"
|
||||
"zh-CN/start/onboarding"
|
||||
]
|
||||
},
|
||||
{
|
||||
"group": "Platforms",
|
||||
"pages": [
|
||||
"zh-CN/platforms/index",
|
||||
"zh-CN/platforms/macos",
|
||||
"zh-CN/platforms/linux",
|
||||
"zh-CN/platforms/windows",
|
||||
"zh-CN/platforms/android",
|
||||
"zh-CN/platforms/ios"
|
||||
]
|
||||
"group": "指南",
|
||||
"pages": ["zh-CN/start/openclaw"]
|
||||
}
|
||||
]
|
||||
},
|
||||
{
|
||||
"tab": "Channels",
|
||||
"tab": "安装",
|
||||
"groups": [
|
||||
{
|
||||
"group": "Overview",
|
||||
"group": "安装概览",
|
||||
"pages": ["zh-CN/install/index", "zh-CN/install/installer"]
|
||||
},
|
||||
{
|
||||
"group": "安装方式",
|
||||
"pages": [
|
||||
"zh-CN/install/node",
|
||||
"zh-CN/install/docker",
|
||||
"zh-CN/install/nix",
|
||||
"zh-CN/install/ansible",
|
||||
"zh-CN/install/bun"
|
||||
]
|
||||
},
|
||||
{
|
||||
"group": "维护",
|
||||
"pages": [
|
||||
"zh-CN/install/updating",
|
||||
"zh-CN/install/migrating",
|
||||
"zh-CN/install/uninstall"
|
||||
]
|
||||
},
|
||||
{
|
||||
"group": "托管与部署",
|
||||
"pages": [
|
||||
"zh-CN/install/fly",
|
||||
"zh-CN/install/hetzner",
|
||||
"zh-CN/install/gcp",
|
||||
"zh-CN/install/macos-vm",
|
||||
"zh-CN/install/exe-dev",
|
||||
"zh-CN/install/railway",
|
||||
"zh-CN/install/render",
|
||||
"zh-CN/install/northflank"
|
||||
]
|
||||
},
|
||||
{
|
||||
"group": "高级",
|
||||
"pages": ["zh-CN/install/development-channels"]
|
||||
}
|
||||
]
|
||||
},
|
||||
{
|
||||
"tab": "消息渠道",
|
||||
"groups": [
|
||||
{
|
||||
"group": "概览",
|
||||
"pages": ["zh-CN/channels/index"]
|
||||
},
|
||||
{
|
||||
"group": "Messaging platforms",
|
||||
"group": "消息平台",
|
||||
"pages": [
|
||||
"zh-CN/channels/whatsapp",
|
||||
"zh-CN/channels/telegram",
|
||||
@@ -1213,8 +1336,9 @@
|
||||
]
|
||||
},
|
||||
{
|
||||
"group": "Configuration",
|
||||
"group": "配置",
|
||||
"pages": [
|
||||
"zh-CN/start/pairing",
|
||||
"zh-CN/concepts/group-messages",
|
||||
"zh-CN/concepts/groups",
|
||||
"zh-CN/broadcast-groups",
|
||||
@@ -1226,10 +1350,10 @@
|
||||
]
|
||||
},
|
||||
{
|
||||
"tab": "Agents",
|
||||
"tab": "代理",
|
||||
"groups": [
|
||||
{
|
||||
"group": "Fundamentals",
|
||||
"group": "基础",
|
||||
"pages": [
|
||||
"zh-CN/concepts/architecture",
|
||||
"zh-CN/concepts/agent",
|
||||
@@ -1241,7 +1365,7 @@
|
||||
]
|
||||
},
|
||||
{
|
||||
"group": "Sessions and memory",
|
||||
"group": "会话与记忆",
|
||||
"pages": [
|
||||
"zh-CN/concepts/session",
|
||||
"zh-CN/concepts/sessions",
|
||||
@@ -1252,11 +1376,11 @@
|
||||
]
|
||||
},
|
||||
{
|
||||
"group": "Multi-agent",
|
||||
"group": "多代理",
|
||||
"pages": ["zh-CN/concepts/multi-agent", "zh-CN/concepts/presence"]
|
||||
},
|
||||
{
|
||||
"group": "Messages and delivery",
|
||||
"group": "消息与投递",
|
||||
"pages": [
|
||||
"zh-CN/concepts/messages",
|
||||
"zh-CN/concepts/streaming",
|
||||
@@ -1267,14 +1391,14 @@
|
||||
]
|
||||
},
|
||||
{
|
||||
"tab": "Tools",
|
||||
"tab": "工具",
|
||||
"groups": [
|
||||
{
|
||||
"group": "Overview",
|
||||
"group": "概览",
|
||||
"pages": ["zh-CN/tools/index"]
|
||||
},
|
||||
{
|
||||
"group": "Built-in tools",
|
||||
"group": "内置工具",
|
||||
"pages": [
|
||||
"zh-CN/tools/lobster",
|
||||
"zh-CN/tools/llm-task",
|
||||
@@ -1287,7 +1411,7 @@
|
||||
]
|
||||
},
|
||||
{
|
||||
"group": "Browser",
|
||||
"group": "浏览器",
|
||||
"pages": [
|
||||
"zh-CN/tools/browser",
|
||||
"zh-CN/tools/browser-login",
|
||||
@@ -1296,7 +1420,7 @@
|
||||
]
|
||||
},
|
||||
{
|
||||
"group": "Agent coordination",
|
||||
"group": "代理协作",
|
||||
"pages": [
|
||||
"zh-CN/tools/agent-send",
|
||||
"zh-CN/tools/subagents",
|
||||
@@ -1304,7 +1428,7 @@
|
||||
]
|
||||
},
|
||||
{
|
||||
"group": "Skills and extensions",
|
||||
"group": "技能与扩展",
|
||||
"pages": [
|
||||
"zh-CN/tools/slash-commands",
|
||||
"zh-CN/tools/skills",
|
||||
@@ -1316,7 +1440,7 @@
|
||||
]
|
||||
},
|
||||
{
|
||||
"group": "Automation",
|
||||
"group": "自动化",
|
||||
"pages": [
|
||||
"zh-CN/hooks",
|
||||
"zh-CN/hooks/soul-evil",
|
||||
@@ -1329,7 +1453,7 @@
|
||||
]
|
||||
},
|
||||
{
|
||||
"group": "Media and devices",
|
||||
"group": "媒体与设备",
|
||||
"pages": [
|
||||
"zh-CN/nodes/index",
|
||||
"zh-CN/nodes/images",
|
||||
@@ -1343,10 +1467,10 @@
|
||||
]
|
||||
},
|
||||
{
|
||||
"tab": "Models",
|
||||
"tab": "模型",
|
||||
"groups": [
|
||||
{
|
||||
"group": "Overview",
|
||||
"group": "概览",
|
||||
"pages": [
|
||||
"zh-CN/providers/index",
|
||||
"zh-CN/providers/models",
|
||||
@@ -1354,11 +1478,11 @@
|
||||
]
|
||||
},
|
||||
{
|
||||
"group": "Configuration",
|
||||
"group": "配置",
|
||||
"pages": ["zh-CN/concepts/model-providers", "zh-CN/concepts/model-failover"]
|
||||
},
|
||||
{
|
||||
"group": "Providers",
|
||||
"group": "提供商",
|
||||
"pages": [
|
||||
"zh-CN/providers/anthropic",
|
||||
"zh-CN/providers/openai",
|
||||
@@ -1376,89 +1500,21 @@
|
||||
]
|
||||
},
|
||||
{
|
||||
"tab": "Infrastructure",
|
||||
"tab": "平台",
|
||||
"groups": [
|
||||
{
|
||||
"group": "Gateway",
|
||||
"group": "平台概览",
|
||||
"pages": [
|
||||
"zh-CN/gateway/index",
|
||||
{
|
||||
"group": "Configuration and operations",
|
||||
"pages": [
|
||||
"zh-CN/gateway/configuration",
|
||||
"zh-CN/gateway/configuration-examples",
|
||||
"zh-CN/gateway/authentication",
|
||||
"zh-CN/gateway/health",
|
||||
"zh-CN/gateway/heartbeat",
|
||||
"zh-CN/gateway/doctor",
|
||||
"zh-CN/gateway/logging",
|
||||
"zh-CN/gateway/gateway-lock",
|
||||
"zh-CN/gateway/background-process",
|
||||
"zh-CN/gateway/multiple-gateways",
|
||||
"zh-CN/gateway/troubleshooting"
|
||||
]
|
||||
},
|
||||
{
|
||||
"group": "Security and sandboxing",
|
||||
"pages": [
|
||||
"zh-CN/gateway/security/index",
|
||||
"zh-CN/gateway/sandboxing",
|
||||
"zh-CN/gateway/sandbox-vs-tool-policy-vs-elevated"
|
||||
]
|
||||
},
|
||||
{
|
||||
"group": "Protocols and APIs",
|
||||
"pages": [
|
||||
"zh-CN/gateway/protocol",
|
||||
"zh-CN/gateway/bridge-protocol",
|
||||
"zh-CN/gateway/openai-http-api",
|
||||
"zh-CN/gateway/tools-invoke-http-api",
|
||||
"zh-CN/gateway/cli-backends",
|
||||
"zh-CN/gateway/local-models"
|
||||
]
|
||||
},
|
||||
{
|
||||
"group": "Networking and discovery",
|
||||
"pages": [
|
||||
"zh-CN/gateway/pairing",
|
||||
"zh-CN/gateway/discovery",
|
||||
"zh-CN/gateway/bonjour"
|
||||
]
|
||||
}
|
||||
"zh-CN/platforms/index",
|
||||
"zh-CN/platforms/macos",
|
||||
"zh-CN/platforms/linux",
|
||||
"zh-CN/platforms/windows",
|
||||
"zh-CN/platforms/android",
|
||||
"zh-CN/platforms/ios"
|
||||
]
|
||||
},
|
||||
{
|
||||
"group": "Remote access and deployment",
|
||||
"pages": [
|
||||
"zh-CN/gateway/remote",
|
||||
"zh-CN/gateway/remote-gateway-readme",
|
||||
"zh-CN/gateway/tailscale",
|
||||
"zh-CN/platforms/fly",
|
||||
"zh-CN/platforms/hetzner",
|
||||
"zh-CN/platforms/gcp",
|
||||
"zh-CN/platforms/macos-vm",
|
||||
"zh-CN/platforms/exe-dev",
|
||||
"zh-CN/railway",
|
||||
"zh-CN/render",
|
||||
"zh-CN/northflank"
|
||||
]
|
||||
},
|
||||
{
|
||||
"group": "Security",
|
||||
"pages": ["zh-CN/security/formal-verification"]
|
||||
},
|
||||
{
|
||||
"group": "Web interfaces",
|
||||
"pages": [
|
||||
"zh-CN/web/index",
|
||||
"zh-CN/web/control-ui",
|
||||
"zh-CN/web/dashboard",
|
||||
"zh-CN/web/webchat",
|
||||
"zh-CN/tui"
|
||||
]
|
||||
},
|
||||
{
|
||||
"group": "macOS companion app",
|
||||
"group": "macOS 配套应用",
|
||||
"pages": [
|
||||
"zh-CN/platforms/mac/dev-setup",
|
||||
"zh-CN/platforms/mac/menu-bar",
|
||||
@@ -1483,10 +1539,87 @@
|
||||
]
|
||||
},
|
||||
{
|
||||
"tab": "Reference",
|
||||
"tab": "网关与运维",
|
||||
"groups": [
|
||||
{
|
||||
"group": "CLI commands",
|
||||
"group": "网关",
|
||||
"pages": [
|
||||
"zh-CN/gateway/index",
|
||||
{
|
||||
"group": "配置与运维",
|
||||
"pages": [
|
||||
"zh-CN/gateway/configuration",
|
||||
"zh-CN/gateway/configuration-examples",
|
||||
"zh-CN/gateway/authentication",
|
||||
"zh-CN/gateway/health",
|
||||
"zh-CN/gateway/heartbeat",
|
||||
"zh-CN/gateway/doctor",
|
||||
"zh-CN/gateway/logging",
|
||||
"zh-CN/gateway/gateway-lock",
|
||||
"zh-CN/gateway/background-process",
|
||||
"zh-CN/gateway/multiple-gateways",
|
||||
"zh-CN/gateway/troubleshooting"
|
||||
]
|
||||
},
|
||||
{
|
||||
"group": "安全与沙箱",
|
||||
"pages": [
|
||||
"zh-CN/gateway/security/index",
|
||||
"zh-CN/gateway/sandboxing",
|
||||
"zh-CN/gateway/sandbox-vs-tool-policy-vs-elevated"
|
||||
]
|
||||
},
|
||||
{
|
||||
"group": "协议与 API",
|
||||
"pages": [
|
||||
"zh-CN/gateway/protocol",
|
||||
"zh-CN/gateway/bridge-protocol",
|
||||
"zh-CN/gateway/openai-http-api",
|
||||
"zh-CN/gateway/tools-invoke-http-api",
|
||||
"zh-CN/gateway/cli-backends",
|
||||
"zh-CN/gateway/local-models"
|
||||
]
|
||||
},
|
||||
{
|
||||
"group": "网络与发现",
|
||||
"pages": [
|
||||
"zh-CN/gateway/network-model",
|
||||
"zh-CN/gateway/pairing",
|
||||
"zh-CN/gateway/discovery",
|
||||
"zh-CN/gateway/bonjour"
|
||||
]
|
||||
}
|
||||
]
|
||||
},
|
||||
{
|
||||
"group": "远程访问",
|
||||
"pages": [
|
||||
"zh-CN/gateway/remote",
|
||||
"zh-CN/gateway/remote-gateway-readme",
|
||||
"zh-CN/gateway/tailscale"
|
||||
]
|
||||
},
|
||||
{
|
||||
"group": "安全",
|
||||
"pages": ["zh-CN/security/formal-verification"]
|
||||
},
|
||||
{
|
||||
"group": "Web 界面",
|
||||
"pages": [
|
||||
"zh-CN/web/index",
|
||||
"zh-CN/web/control-ui",
|
||||
"zh-CN/web/dashboard",
|
||||
"zh-CN/web/webchat",
|
||||
"zh-CN/tui"
|
||||
]
|
||||
}
|
||||
]
|
||||
},
|
||||
{
|
||||
"tab": "参考",
|
||||
"groups": [
|
||||
{
|
||||
"group": "CLI 命令",
|
||||
"pages": [
|
||||
"zh-CN/cli/index",
|
||||
"zh-CN/cli/agent",
|
||||
@@ -1527,11 +1660,11 @@
|
||||
]
|
||||
},
|
||||
{
|
||||
"group": "RPC and API",
|
||||
"group": "RPC 与 API",
|
||||
"pages": ["zh-CN/reference/rpc", "zh-CN/reference/device-models"]
|
||||
},
|
||||
{
|
||||
"group": "Templates",
|
||||
"group": "模板",
|
||||
"pages": [
|
||||
"zh-CN/reference/AGENTS.default",
|
||||
"zh-CN/reference/templates/AGENTS",
|
||||
@@ -1545,7 +1678,7 @@
|
||||
]
|
||||
},
|
||||
{
|
||||
"group": "Technical reference",
|
||||
"group": "技术参考",
|
||||
"pages": [
|
||||
"zh-CN/concepts/typebox",
|
||||
"zh-CN/concepts/markdown-formatting",
|
||||
@@ -1556,20 +1689,28 @@
|
||||
]
|
||||
},
|
||||
{
|
||||
"group": "Release notes",
|
||||
"group": "项目",
|
||||
"pages": ["zh-CN/reference/credits"]
|
||||
},
|
||||
{
|
||||
"group": "发布说明",
|
||||
"pages": ["zh-CN/reference/RELEASING", "zh-CN/reference/test"]
|
||||
}
|
||||
]
|
||||
},
|
||||
{
|
||||
"tab": "Help",
|
||||
"tab": "帮助",
|
||||
"groups": [
|
||||
{
|
||||
"group": "Help",
|
||||
"group": "帮助",
|
||||
"pages": ["zh-CN/help/index", "zh-CN/help/troubleshooting", "zh-CN/help/faq"]
|
||||
},
|
||||
{
|
||||
"group": "Environment and debugging",
|
||||
"group": "社区",
|
||||
"pages": ["zh-CN/start/lore"]
|
||||
},
|
||||
{
|
||||
"group": "环境与调试",
|
||||
"pages": [
|
||||
"zh-CN/environment",
|
||||
"zh-CN/debugging",
|
||||
@@ -1577,6 +1718,14 @@
|
||||
"zh-CN/scripts",
|
||||
"zh-CN/reference/session-management-compaction"
|
||||
]
|
||||
},
|
||||
{
|
||||
"group": "开发者工作流",
|
||||
"pages": ["zh-CN/start/setup"]
|
||||
},
|
||||
{
|
||||
"group": "文档元信息",
|
||||
"pages": ["zh-CN/start/hubs", "zh-CN/start/docs-directory"]
|
||||
}
|
||||
]
|
||||
}
|
||||
|
||||
@@ -25,13 +25,13 @@ want “always works” text responses without relying on external APIs.
|
||||
You can use Claude Code CLI **without any config** (OpenClaw ships a built-in default):
|
||||
|
||||
```bash
|
||||
openclaw agent --message "hi" --model claude-cli/opus-4.5
|
||||
openclaw agent --message "hi" --model claude-cli/opus-4.6
|
||||
```
|
||||
|
||||
Codex CLI also works out of the box:
|
||||
|
||||
```bash
|
||||
openclaw agent --message "hi" --model codex-cli/gpt-5.2-codex
|
||||
openclaw agent --message "hi" --model codex-cli/gpt-5.3-codex
|
||||
```
|
||||
|
||||
If your gateway runs under launchd/systemd and PATH is minimal, add just the
|
||||
@@ -62,11 +62,12 @@ Add a CLI backend to your fallback list so it only runs when primary models fail
|
||||
agents: {
|
||||
defaults: {
|
||||
model: {
|
||||
primary: "anthropic/claude-opus-4-5",
|
||||
fallbacks: ["claude-cli/opus-4.5"],
|
||||
primary: "anthropic/claude-opus-4-6",
|
||||
fallbacks: ["claude-cli/opus-4.6", "claude-cli/opus-4.5"],
|
||||
},
|
||||
models: {
|
||||
"anthropic/claude-opus-4-5": { alias: "Opus" },
|
||||
"anthropic/claude-opus-4-6": { alias: "Opus" },
|
||||
"claude-cli/opus-4.6": {},
|
||||
"claude-cli/opus-4.5": {},
|
||||
},
|
||||
},
|
||||
@@ -112,6 +113,7 @@ The provider id becomes the left side of your model ref:
|
||||
input: "arg",
|
||||
modelArg: "--model",
|
||||
modelAliases: {
|
||||
"claude-opus-4-6": "opus",
|
||||
"claude-opus-4-5": "opus",
|
||||
"claude-sonnet-4-5": "sonnet",
|
||||
},
|
||||
|
||||
@@ -226,13 +226,13 @@ Save to `~/.openclaw/openclaw.json` and you can DM the bot from that number.
|
||||
userTimezone: "America/Chicago",
|
||||
model: {
|
||||
primary: "anthropic/claude-sonnet-4-5",
|
||||
fallbacks: ["anthropic/claude-opus-4-5", "openai/gpt-5.2"],
|
||||
fallbacks: ["anthropic/claude-opus-4-6", "openai/gpt-5.2"],
|
||||
},
|
||||
imageModel: {
|
||||
primary: "openrouter/anthropic/claude-sonnet-4-5",
|
||||
},
|
||||
models: {
|
||||
"anthropic/claude-opus-4-5": { alias: "opus" },
|
||||
"anthropic/claude-opus-4-6": { alias: "opus" },
|
||||
"anthropic/claude-sonnet-4-5": { alias: "sonnet" },
|
||||
"openai/gpt-5.2": { alias: "gpt" },
|
||||
},
|
||||
@@ -496,7 +496,7 @@ If more than one person can DM your bot (multiple entries in `allowFrom`, pairin
|
||||
workspace: "~/.openclaw/workspace",
|
||||
model: {
|
||||
primary: "anthropic/claude-sonnet-4-5",
|
||||
fallbacks: ["anthropic/claude-opus-4-5"],
|
||||
fallbacks: ["anthropic/claude-opus-4-6"],
|
||||
},
|
||||
},
|
||||
}
|
||||
@@ -534,7 +534,7 @@ If more than one person can DM your bot (multiple entries in `allowFrom`, pairin
|
||||
agent: {
|
||||
workspace: "~/.openclaw/workspace",
|
||||
model: {
|
||||
primary: "anthropic/claude-opus-4-5",
|
||||
primary: "anthropic/claude-opus-4-6",
|
||||
fallbacks: ["minimax/MiniMax-M2.1"],
|
||||
},
|
||||
},
|
||||
|
||||
@@ -1517,6 +1517,25 @@ See [Messages](/concepts/messages) for queueing, sessions, and streaming context
|
||||
`responsePrefix` is applied to **all outbound replies** (tool summaries, block
|
||||
streaming, final replies) across channels unless already present.
|
||||
|
||||
Overrides can be configured per channel and per account:
|
||||
|
||||
- `channels.<channel>.responsePrefix`
|
||||
- `channels.<channel>.accounts.<id>.responsePrefix`
|
||||
|
||||
Resolution order (most specific wins):
|
||||
|
||||
1. `channels.<channel>.accounts.<id>.responsePrefix`
|
||||
2. `channels.<channel>.responsePrefix`
|
||||
3. `messages.responsePrefix`
|
||||
|
||||
Semantics:
|
||||
|
||||
- `undefined` falls through to the next level.
|
||||
- `""` explicitly disables the prefix and stops the cascade.
|
||||
- `"auto"` derives `[{identity.name}]` for the routed agent.
|
||||
|
||||
Overrides apply to all channels, including extensions, and to every outbound reply kind.
|
||||
|
||||
If `messages.responsePrefix` is unset, no prefix is applied by default. WhatsApp self-chat
|
||||
replies are the exception: they default to `[{identity.name}]` when set, otherwise
|
||||
`[openclaw]`, so same-phone conversations stay legible.
|
||||
@@ -1528,8 +1547,8 @@ The `responsePrefix` string can include template variables that resolve dynamica
|
||||
|
||||
| Variable | Description | Example |
|
||||
| ----------------- | ---------------------- | --------------------------- |
|
||||
| `{model}` | Short model name | `claude-opus-4-5`, `gpt-4o` |
|
||||
| `{modelFull}` | Full model identifier | `anthropic/claude-opus-4-5` |
|
||||
| `{model}` | Short model name | `claude-opus-4-6`, `gpt-4o` |
|
||||
| `{modelFull}` | Full model identifier | `anthropic/claude-opus-4-6` |
|
||||
| `{provider}` | Provider name | `anthropic`, `openai` |
|
||||
| `{thinkingLevel}` | Current thinking level | `high`, `low`, `off` |
|
||||
| `{identity.name}` | Agent identity name | (same as `"auto"` mode) |
|
||||
@@ -1545,7 +1564,7 @@ Unresolved variables remain as literal text.
|
||||
}
|
||||
```
|
||||
|
||||
Example output: `[claude-opus-4-5 | think:high] Here's my response...`
|
||||
Example output: `[claude-opus-4-6 | think:high] Here's my response...`
|
||||
|
||||
WhatsApp inbound prefix is configured via `channels.whatsapp.messagePrefix` (deprecated:
|
||||
`messages.messagePrefix`). Default stays **unchanged**: `"[openclaw]"` when
|
||||
@@ -1691,7 +1710,7 @@ Z.AI GLM-4.x models automatically enable thinking mode unless you:
|
||||
OpenClaw also ships a few built-in alias shorthands. Defaults only apply when the model
|
||||
is already present in `agents.defaults.models`:
|
||||
|
||||
- `opus` -> `anthropic/claude-opus-4-5`
|
||||
- `opus` -> `anthropic/claude-opus-4-6`
|
||||
- `sonnet` -> `anthropic/claude-sonnet-4-5`
|
||||
- `gpt` -> `openai/gpt-5.2`
|
||||
- `gpt-mini` -> `openai/gpt-5-mini`
|
||||
@@ -1700,18 +1719,18 @@ is already present in `agents.defaults.models`:
|
||||
|
||||
If you configure the same alias name (case-insensitive) yourself, your value wins (defaults never override).
|
||||
|
||||
Example: Opus 4.5 primary with MiniMax M2.1 fallback (hosted MiniMax):
|
||||
Example: Opus 4.6 primary with MiniMax M2.1 fallback (hosted MiniMax):
|
||||
|
||||
```json5
|
||||
{
|
||||
agents: {
|
||||
defaults: {
|
||||
models: {
|
||||
"anthropic/claude-opus-4-5": { alias: "opus" },
|
||||
"anthropic/claude-opus-4-6": { alias: "opus" },
|
||||
"minimax/MiniMax-M2.1": { alias: "minimax" },
|
||||
},
|
||||
model: {
|
||||
primary: "anthropic/claude-opus-4-5",
|
||||
primary: "anthropic/claude-opus-4-6",
|
||||
fallbacks: ["minimax/MiniMax-M2.1"],
|
||||
},
|
||||
},
|
||||
@@ -1767,7 +1786,7 @@ Example:
|
||||
agents: {
|
||||
defaults: {
|
||||
models: {
|
||||
"anthropic/claude-opus-4-5": { alias: "Opus" },
|
||||
"anthropic/claude-opus-4-6": { alias: "Opus" },
|
||||
"anthropic/claude-sonnet-4-1": { alias: "Sonnet" },
|
||||
"openrouter/deepseek/deepseek-r1:free": {},
|
||||
"zai/glm-4.7": {
|
||||
@@ -1781,7 +1800,7 @@ Example:
|
||||
},
|
||||
},
|
||||
model: {
|
||||
primary: "anthropic/claude-opus-4-5",
|
||||
primary: "anthropic/claude-opus-4-6",
|
||||
fallbacks: [
|
||||
"openrouter/deepseek/deepseek-r1:free",
|
||||
"openrouter/meta-llama/llama-3.3-70b-instruct:free",
|
||||
@@ -1992,7 +2011,7 @@ Typing indicators:
|
||||
- `session.typingIntervalSeconds`: per-session override for the refresh interval.
|
||||
See [/concepts/typing-indicators](/concepts/typing-indicators) for behavior details.
|
||||
|
||||
`agents.defaults.model.primary` should be set as `provider/model` (e.g. `anthropic/claude-opus-4-5`).
|
||||
`agents.defaults.model.primary` should be set as `provider/model` (e.g. `anthropic/claude-opus-4-6`).
|
||||
Aliases come from `agents.defaults.models.*.alias` (e.g. `Opus`).
|
||||
If you omit the provider, OpenClaw currently assumes `anthropic` as a temporary
|
||||
deprecation fallback.
|
||||
@@ -2466,7 +2485,7 @@ the built-in `opencode` provider from pi-ai; set `OPENCODE_API_KEY` (or
|
||||
|
||||
Notes:
|
||||
|
||||
- Model refs use `opencode/<modelId>` (example: `opencode/claude-opus-4-5`).
|
||||
- Model refs use `opencode/<modelId>` (example: `opencode/claude-opus-4-6`).
|
||||
- If you enable an allowlist via `agents.defaults.models`, add each model you plan to use.
|
||||
- Shortcut: `openclaw onboard --auth-choice opencode-zen`.
|
||||
|
||||
@@ -2474,8 +2493,8 @@ Notes:
|
||||
{
|
||||
agents: {
|
||||
defaults: {
|
||||
model: { primary: "opencode/claude-opus-4-5" },
|
||||
models: { "opencode/claude-opus-4-5": { alias: "Opus" } },
|
||||
model: { primary: "opencode/claude-opus-4-6" },
|
||||
models: { "opencode/claude-opus-4-6": { alias: "Opus" } },
|
||||
},
|
||||
},
|
||||
}
|
||||
@@ -2633,7 +2652,7 @@ Use MiniMax M2.1 directly without LM Studio:
|
||||
agent: {
|
||||
model: { primary: "minimax/MiniMax-M2.1" },
|
||||
models: {
|
||||
"anthropic/claude-opus-4-5": { alias: "Opus" },
|
||||
"anthropic/claude-opus-4-6": { alias: "Opus" },
|
||||
"minimax/MiniMax-M2.1": { alias: "Minimax" },
|
||||
},
|
||||
},
|
||||
|
||||
@@ -83,10 +83,11 @@ and logged; a message that is only `HEARTBEAT_OK` is dropped.
|
||||
defaults: {
|
||||
heartbeat: {
|
||||
every: "30m", // default: 30m (0m disables)
|
||||
model: "anthropic/claude-opus-4-5",
|
||||
model: "anthropic/claude-opus-4-6",
|
||||
includeReasoning: false, // default: false (deliver separate Reasoning: message when available)
|
||||
target: "last", // last | none | <channel id> (core or plugin, e.g. "bluebubbles")
|
||||
to: "+15551234567", // optional channel-specific override
|
||||
accountId: "ops-bot", // optional multi-account channel id
|
||||
prompt: "Read HEARTBEAT.md if it exists (workspace context). Follow it strictly. Do not infer or repeat old tasks from prior chats. If nothing needs attention, reply HEARTBEAT_OK.",
|
||||
ackMaxChars: 300, // max chars allowed after HEARTBEAT_OK
|
||||
},
|
||||
@@ -136,6 +137,35 @@ Example: two agents, only the second agent runs heartbeats.
|
||||
}
|
||||
```
|
||||
|
||||
### Multi account example
|
||||
|
||||
Use `accountId` to target a specific account on multi-account channels like Telegram:
|
||||
|
||||
```json5
|
||||
{
|
||||
agents: {
|
||||
list: [
|
||||
{
|
||||
id: "ops",
|
||||
heartbeat: {
|
||||
every: "1h",
|
||||
target: "telegram",
|
||||
to: "12345678",
|
||||
accountId: "ops-bot",
|
||||
},
|
||||
},
|
||||
],
|
||||
},
|
||||
channels: {
|
||||
telegram: {
|
||||
accounts: {
|
||||
"ops-bot": { botToken: "YOUR_TELEGRAM_BOT_TOKEN" },
|
||||
},
|
||||
},
|
||||
},
|
||||
}
|
||||
```
|
||||
|
||||
### Field notes
|
||||
|
||||
- `every`: heartbeat interval (duration string; default unit = minutes).
|
||||
@@ -150,6 +180,7 @@ Example: two agents, only the second agent runs heartbeats.
|
||||
- explicit channel: `whatsapp` / `telegram` / `discord` / `googlechat` / `slack` / `msteams` / `signal` / `imessage`.
|
||||
- `none`: run the heartbeat but **do not deliver** externally.
|
||||
- `to`: optional recipient override (channel-specific id, e.g. E.164 for WhatsApp or a Telegram chat id).
|
||||
- `accountId`: optional account id for multi-account channels. When `target: "last"`, the account id applies to the resolved last channel if it supports accounts; otherwise it is ignored. If the account id does not match a configured account for the resolved channel, delivery is skipped.
|
||||
- `prompt`: overrides the default prompt body (not merged).
|
||||
- `ackMaxChars`: max chars allowed after `HEARTBEAT_OK` before delivery.
|
||||
|
||||
|
||||
@@ -21,7 +21,7 @@ Best current local stack. Load MiniMax M2.1 in LM Studio, enable the local serve
|
||||
defaults: {
|
||||
model: { primary: "lmstudio/minimax-m2.1-gs32" },
|
||||
models: {
|
||||
"anthropic/claude-opus-4-5": { alias: "Opus" },
|
||||
"anthropic/claude-opus-4-6": { alias: "Opus" },
|
||||
"lmstudio/minimax-m2.1-gs32": { alias: "Minimax" },
|
||||
},
|
||||
},
|
||||
@@ -68,12 +68,12 @@ Keep hosted models configured even when running local; use `models.mode: "merge"
|
||||
defaults: {
|
||||
model: {
|
||||
primary: "anthropic/claude-sonnet-4-5",
|
||||
fallbacks: ["lmstudio/minimax-m2.1-gs32", "anthropic/claude-opus-4-5"],
|
||||
fallbacks: ["lmstudio/minimax-m2.1-gs32", "anthropic/claude-opus-4-6"],
|
||||
},
|
||||
models: {
|
||||
"anthropic/claude-sonnet-4-5": { alias: "Sonnet" },
|
||||
"lmstudio/minimax-m2.1-gs32": { alias: "MiniMax Local" },
|
||||
"anthropic/claude-opus-4-5": { alias: "Opus" },
|
||||
"anthropic/claude-opus-4-6": { alias: "Opus" },
|
||||
},
|
||||
},
|
||||
},
|
||||
|
||||
17
docs/gateway/network-model.md
Normal file
17
docs/gateway/network-model.md
Normal file
@@ -0,0 +1,17 @@
|
||||
---
|
||||
summary: "How the Gateway, nodes, and canvas host connect."
|
||||
read_when:
|
||||
- You want a concise view of the Gateway networking model
|
||||
title: "Network model"
|
||||
---
|
||||
|
||||
Most operations flow through the Gateway (`openclaw gateway`), a single long-running
|
||||
process that owns channel connections and the WebSocket control plane.
|
||||
|
||||
## Core rules
|
||||
|
||||
- One Gateway per host is recommended. It is the only process allowed to own the WhatsApp Web session. For rescue bots or strict isolation, run multiple gateways with isolated profiles and ports. See [Multiple gateways](/gateway/multiple-gateways).
|
||||
- Loopback first: the Gateway WS defaults to `ws://127.0.0.1:18789`. The wizard generates a gateway token by default, even for loopback. For tailnet access, run `openclaw gateway --bind tailnet --token ...` because tokens are required for non-loopback binds.
|
||||
- Nodes connect to the Gateway WS over LAN, tailnet, or SSH as needed. The legacy TCP bridge is deprecated.
|
||||
- Canvas host is an HTTP file server on `canvasHost.port` (default `18793`) serving `/__openclaw__/canvas/` for node WebViews. See [Gateway configuration](/gateway/configuration) (`canvasHost`).
|
||||
- Remote use is typically SSH tunnel or tailnet VPN. See [Remote access](/gateway/remote) and [Discovery](/gateway/discovery).
|
||||
@@ -28,7 +28,7 @@ Run the Gateway on a persistent host and reach it via **Tailscale** or SSH.
|
||||
|
||||
- **Best UX:** keep `gateway.bind: "loopback"` and use **Tailscale Serve** for the Control UI.
|
||||
- **Fallback:** keep loopback + SSH tunnel from any machine that needs access.
|
||||
- **Examples:** [exe.dev](/platforms/exe-dev) (easy VM) or [Hetzner](/platforms/hetzner) (production VPS).
|
||||
- **Examples:** [exe.dev](/install/exe-dev) (easy VM) or [Hetzner](/install/hetzner) (production VPS).
|
||||
|
||||
This is ideal when your laptop sleeps often but you want the agent always-on.
|
||||
|
||||
@@ -80,6 +80,8 @@ With the tunnel up:
|
||||
- `openclaw gateway {status,health,send,agent,call}` can also target the forwarded URL via `--url` when needed.
|
||||
|
||||
Note: replace `18789` with your configured `gateway.port` (or `--port`/`OPENCLAW_GATEWAY_PORT`).
|
||||
Note: when you pass `--url`, the CLI does not fall back to config or environment credentials.
|
||||
Include `--token` or `--password` explicitly. Missing explicit credentials is an error.
|
||||
|
||||
## CLI remote defaults
|
||||
|
||||
|
||||
@@ -243,7 +243,7 @@ Even with strong system prompts, **prompt injection is not solved**. System prom
|
||||
- Run sensitive tool execution in a sandbox; keep secrets out of the agent’s reachable filesystem.
|
||||
- Note: sandboxing is opt-in. If sandbox mode is off, exec runs on the gateway host even though tools.exec.host defaults to sandbox, and host exec does not require approvals unless you set host=gateway and configure exec approvals.
|
||||
- Limit high-risk tools (`exec`, `browser`, `web_fetch`, `web_search`) to trusted agents or explicit allowlists.
|
||||
- **Model choice matters:** older/legacy models can be less robust against prompt injection and tool misuse. Prefer modern, instruction-hardened models for any bot with tools. We recommend Anthropic Opus 4.5 because it’s quite good at recognizing prompt injections (see [“A step forward on safety”](https://www.anthropic.com/news/claude-opus-4-5)).
|
||||
- **Model choice matters:** older/legacy models can be less robust against prompt injection and tool misuse. Prefer modern, instruction-hardened models for any bot with tools. We recommend Anthropic Opus 4.6 (or the latest Opus) because it’s strong at recognizing prompt injections (see [“A step forward on safety”](https://www.anthropic.com/news/claude-opus-4-5)).
|
||||
|
||||
Red flags to treat as untrusted:
|
||||
|
||||
|
||||
@@ -141,7 +141,7 @@ Quick answers plus deeper troubleshooting for real-world setups (local dev, VPS,
|
||||
- [Can I use self-hosted models (llama.cpp, vLLM, Ollama)?](#can-i-use-selfhosted-models-llamacpp-vllm-ollama)
|
||||
- [What do OpenClaw, Flawd, and Krill use for models?](#what-do-openclaw-flawd-and-krill-use-for-models)
|
||||
- [How do I switch models on the fly (without restarting)?](#how-do-i-switch-models-on-the-fly-without-restarting)
|
||||
- [Can I use GPT 5.2 for daily tasks and Codex 5.2 for coding](#can-i-use-gpt-52-for-daily-tasks-and-codex-52-for-coding)
|
||||
- [Can I use GPT 5.2 for daily tasks and Codex 5.3 for coding](#can-i-use-gpt-52-for-daily-tasks-and-codex-53-for-coding)
|
||||
- [Why do I see "Model … is not allowed" and then no reply?](#why-do-i-see-model-is-not-allowed-and-then-no-reply)
|
||||
- [Why do I see "Unknown model: minimax/MiniMax-M2.1"?](#why-do-i-see-unknown-model-minimaxminimaxm21)
|
||||
- [Can I use MiniMax as my default and OpenAI for complex tasks?](#can-i-use-minimax-as-my-default-and-openai-for-complex-tasks)
|
||||
@@ -591,7 +591,7 @@ Short answer: follow the Linux guide, then run the onboarding wizard.
|
||||
|
||||
Any Linux VPS works. Install on the server, then use SSH/Tailscale to reach the Gateway.
|
||||
|
||||
Guides: [exe.dev](/platforms/exe-dev), [Hetzner](/platforms/hetzner), [Fly.io](/platforms/fly).
|
||||
Guides: [exe.dev](/install/exe-dev), [Hetzner](/install/hetzner), [Fly.io](/install/fly).
|
||||
Remote access: [Gateway remote](/gateway/remote).
|
||||
|
||||
### Where are the cloudVPS install guides
|
||||
@@ -599,9 +599,9 @@ Remote access: [Gateway remote](/gateway/remote).
|
||||
We keep a **hosting hub** with the common providers. Pick one and follow the guide:
|
||||
|
||||
- [VPS hosting](/vps) (all providers in one place)
|
||||
- [Fly.io](/platforms/fly)
|
||||
- [Hetzner](/platforms/hetzner)
|
||||
- [exe.dev](/platforms/exe-dev)
|
||||
- [Fly.io](/install/fly)
|
||||
- [Hetzner](/install/hetzner)
|
||||
- [exe.dev](/install/exe-dev)
|
||||
|
||||
How it works in the cloud: the **Gateway runs on the server**, and you access it
|
||||
from your laptop/phone via the Control UI (or Tailscale/SSH). Your state + workspace
|
||||
@@ -707,7 +707,7 @@ Yes - via pi-ai's **Amazon Bedrock (Converse)** provider with **manual config**.
|
||||
|
||||
### How does Codex auth work
|
||||
|
||||
OpenClaw supports **OpenAI Code (Codex)** via OAuth (ChatGPT sign-in). The wizard can run the OAuth flow and will set the default model to `openai-codex/gpt-5.2` when appropriate. See [Model providers](/concepts/model-providers) and [Wizard](/start/wizard).
|
||||
OpenClaw supports **OpenAI Code (Codex)** via OAuth (ChatGPT sign-in). The wizard can run the OAuth flow and will set the default model to `openai-codex/gpt-5.3-codex` when appropriate. See [Model providers](/concepts/model-providers) and [Wizard](/start/wizard).
|
||||
|
||||
### Do you support OpenAI subscription auth Codex OAuth
|
||||
|
||||
@@ -910,7 +910,7 @@ Baseline guidance:
|
||||
|
||||
If you are on Windows, **WSL2 is the easiest VM style setup** and has the best tooling
|
||||
compatibility. See [Windows](/platforms/windows), [VPS hosting](/vps).
|
||||
If you are running macOS in a VM, see [macOS VM](/platforms/macos-vm).
|
||||
If you are running macOS in a VM, see [macOS VM](/install/macos-vm).
|
||||
|
||||
## What is OpenClaw?
|
||||
|
||||
@@ -1936,11 +1936,11 @@ OpenClaw's default model is whatever you set as:
|
||||
agents.defaults.model.primary
|
||||
```
|
||||
|
||||
Models are referenced as `provider/model` (example: `anthropic/claude-opus-4-5`). If you omit the provider, OpenClaw currently assumes `anthropic` as a temporary deprecation fallback - but you should still **explicitly** set `provider/model`.
|
||||
Models are referenced as `provider/model` (example: `anthropic/claude-opus-4-6`). If you omit the provider, OpenClaw currently assumes `anthropic` as a temporary deprecation fallback - but you should still **explicitly** set `provider/model`.
|
||||
|
||||
### What model do you recommend
|
||||
|
||||
**Recommended default:** `anthropic/claude-opus-4-5`.
|
||||
**Recommended default:** `anthropic/claude-opus-4-6`.
|
||||
**Good alternative:** `anthropic/claude-sonnet-4-5`.
|
||||
**Reliable (less character):** `openai/gpt-5.2` - nearly as good as Opus, just less personality.
|
||||
**Budget:** `zai/glm-4.7`.
|
||||
@@ -1989,7 +1989,7 @@ Docs: [Models](/concepts/models), [Configure](/cli/configure), [Config](/cli/con
|
||||
|
||||
### What do OpenClaw, Flawd, and Krill use for models
|
||||
|
||||
- **OpenClaw + Flawd:** Anthropic Opus (`anthropic/claude-opus-4-5`) - see [Anthropic](/providers/anthropic).
|
||||
- **OpenClaw + Flawd:** Anthropic Opus (`anthropic/claude-opus-4-6`) - see [Anthropic](/providers/anthropic).
|
||||
- **Krill:** MiniMax M2.1 (`minimax/MiniMax-M2.1`) - see [MiniMax](/providers/minimax).
|
||||
|
||||
### How do I switch models on the fly without restarting
|
||||
@@ -2029,18 +2029,18 @@ It also shows the configured provider endpoint (`baseUrl`) and API mode (`api`)
|
||||
Re-run `/model` **without** the `@profile` suffix:
|
||||
|
||||
```
|
||||
/model anthropic/claude-opus-4-5
|
||||
/model anthropic/claude-opus-4-6
|
||||
```
|
||||
|
||||
If you want to return to the default, pick it from `/model` (or send `/model <default provider/model>`).
|
||||
Use `/model status` to confirm which auth profile is active.
|
||||
|
||||
### Can I use GPT 5.2 for daily tasks and Codex 5.2 for coding
|
||||
### Can I use GPT 5.2 for daily tasks and Codex 5.3 for coding
|
||||
|
||||
Yes. Set one as default and switch as needed:
|
||||
|
||||
- **Quick switch (per session):** `/model gpt-5.2` for daily tasks, `/model gpt-5.2-codex` for coding.
|
||||
- **Default + switch:** set `agents.defaults.model.primary` to `openai-codex/gpt-5.2`, then switch to `openai-codex/gpt-5.2-codex` when coding (or the other way around).
|
||||
- **Quick switch (per session):** `/model gpt-5.2` for daily tasks, `/model gpt-5.3-codex` for coding.
|
||||
- **Default + switch:** set `agents.defaults.model.primary` to `openai/gpt-5.2`, then switch to `openai-codex/gpt-5.3-codex` when coding (or the other way around).
|
||||
- **Sub-agents:** route coding tasks to sub-agents with a different default model.
|
||||
|
||||
See [Models](/concepts/models) and [Slash commands](/tools/slash-commands).
|
||||
@@ -2118,7 +2118,7 @@ Docs: [Models](/concepts/models), [Multi-Agent Routing](/concepts/multi-agent),
|
||||
|
||||
Yes. OpenClaw ships a few default shorthands (only applied when the model exists in `agents.defaults.models`):
|
||||
|
||||
- `opus` → `anthropic/claude-opus-4-5`
|
||||
- `opus` → `anthropic/claude-opus-4-6`
|
||||
- `sonnet` → `anthropic/claude-sonnet-4-5`
|
||||
- `gpt` → `openai/gpt-5.2`
|
||||
- `gpt-mini` → `openai/gpt-5-mini`
|
||||
@@ -2135,9 +2135,9 @@ Aliases come from `agents.defaults.models.<modelId>.alias`. Example:
|
||||
{
|
||||
agents: {
|
||||
defaults: {
|
||||
model: { primary: "anthropic/claude-opus-4-5" },
|
||||
model: { primary: "anthropic/claude-opus-4-6" },
|
||||
models: {
|
||||
"anthropic/claude-opus-4-5": { alias: "opus" },
|
||||
"anthropic/claude-opus-4-6": { alias: "opus" },
|
||||
"anthropic/claude-sonnet-4-5": { alias: "sonnet" },
|
||||
"anthropic/claude-haiku-4-5": { alias: "haiku" },
|
||||
},
|
||||
@@ -2823,7 +2823,7 @@ You can add options like `debounce:2s cap:25 drop:summarize` for followup modes.
|
||||
|
||||
**Q: "What's the default model for Anthropic with an API key?"**
|
||||
|
||||
**A:** In OpenClaw, credentials and model selection are separate. Setting `ANTHROPIC_API_KEY` (or storing an Anthropic API key in auth profiles) enables authentication, but the actual default model is whatever you configure in `agents.defaults.model.primary` (for example, `anthropic/claude-sonnet-4-5` or `anthropic/claude-opus-4-5`). If you see `No credentials found for profile "anthropic:default"`, it means the Gateway couldn't find Anthropic credentials in the expected `auth-profiles.json` for the agent that's running.
|
||||
**A:** In OpenClaw, credentials and model selection are separate. Setting `ANTHROPIC_API_KEY` (or storing an Anthropic API key in auth profiles) enables authentication, but the actual default model is whatever you configure in `agents.defaults.model.primary` (for example, `anthropic/claude-sonnet-4-5` or `anthropic/claude-opus-4-6`). If you see `No credentials found for profile "anthropic:default"`, it means the Gateway couldn't find Anthropic credentials in the expected `auth-profiles.json` for the agent that's running.
|
||||
|
||||
---
|
||||
|
||||
|
||||
328
docs/index.md
328
docs/index.md
@@ -1,5 +1,5 @@
|
||||
---
|
||||
summary: "Top-level overview of OpenClaw, features, and purpose"
|
||||
summary: "OpenClaw is a multi-channel gateway for AI agents that runs on any OS."
|
||||
read_when:
|
||||
- Introducing OpenClaw to newcomers
|
||||
title: "OpenClaw"
|
||||
@@ -7,8 +7,6 @@ title: "OpenClaw"
|
||||
|
||||
# OpenClaw 🦞
|
||||
|
||||
> _"EXFOLIATE! EXFOLIATE!"_ — A space lobster, probably
|
||||
|
||||
<p align="center">
|
||||
<img
|
||||
src="/assets/openclaw-logo-text-dark.png"
|
||||
@@ -24,143 +22,111 @@ title: "OpenClaw"
|
||||
/>
|
||||
</p>
|
||||
|
||||
<p align="center">
|
||||
<strong>Any OS + WhatsApp/Telegram/Discord/iMessage gateway for AI agents (Pi).</strong><br />
|
||||
Plugins add Mattermost and more.
|
||||
Send a message, get an agent response — from your pocket.
|
||||
</p>
|
||||
> _"EXFOLIATE! EXFOLIATE!"_ — A space lobster, probably
|
||||
|
||||
<p align="center">
|
||||
<a href="https://github.com/openclaw/openclaw">GitHub</a> ·
|
||||
<a href="https://github.com/openclaw/openclaw/releases">Releases</a> ·
|
||||
<a href="/">Docs</a> ·
|
||||
<a href="/start/openclaw">OpenClaw assistant setup</a>
|
||||
<strong>Any OS gateway for AI agents across WhatsApp, Telegram, Discord, iMessage, and more.</strong><br />
|
||||
Send a message, get an agent response from your pocket. Plugins add Mattermost and more.
|
||||
</p>
|
||||
|
||||
OpenClaw bridges WhatsApp (via WhatsApp Web / Baileys), Telegram (Bot API / grammY), Discord (Bot API / channels.discord.js), and iMessage (imsg CLI) to coding agents like [Pi](https://github.com/badlogic/pi-mono). Plugins add Mattermost (Bot API + WebSocket) and more.
|
||||
OpenClaw also powers the OpenClaw assistant.
|
||||
<Columns>
|
||||
<Card title="Get Started" href="/start/getting-started" icon="rocket">
|
||||
Install OpenClaw and bring up the Gateway in minutes.
|
||||
</Card>
|
||||
<Card title="Run the Wizard" href="/start/wizard" icon="sparkles">
|
||||
Guided setup with `openclaw onboard` and pairing flows.
|
||||
</Card>
|
||||
<Card title="Open the Control UI" href="/web/control-ui" icon="layout-dashboard">
|
||||
Launch the browser dashboard for chat, config, and sessions.
|
||||
</Card>
|
||||
</Columns>
|
||||
|
||||
## Start here
|
||||
## What is OpenClaw?
|
||||
|
||||
- **New install from zero:** [Getting Started](/start/getting-started)
|
||||
- **Guided setup (recommended):** [Wizard](/start/wizard) (`openclaw onboard`)
|
||||
- **Open the dashboard (local Gateway):** http://127.0.0.1:18789/ (or http://localhost:18789/)
|
||||
OpenClaw is a **self-hosted gateway** that connects your favorite chat apps — WhatsApp, Telegram, Discord, iMessage, and more — to AI coding agents like Pi. You run a single Gateway process on your own machine (or a server), and it becomes the bridge between your messaging apps and an always-available AI assistant.
|
||||
|
||||
If the Gateway is running on the same computer, that link opens the browser Control UI
|
||||
immediately. If it fails, start the Gateway first: `openclaw gateway`.
|
||||
**Who is it for?** Developers and power users who want a personal AI assistant they can message from anywhere — without giving up control of their data or relying on a hosted service.
|
||||
|
||||
## Dashboard (browser Control UI)
|
||||
**What makes it different?**
|
||||
|
||||
The dashboard is the browser Control UI for chat, config, nodes, sessions, and more.
|
||||
Local default: http://127.0.0.1:18789/
|
||||
Remote access: [Web surfaces](/web) and [Tailscale](/gateway/tailscale)
|
||||
- **Self-hosted**: runs on your hardware, your rules
|
||||
- **Multi-channel**: one Gateway serves WhatsApp, Telegram, Discord, and more simultaneously
|
||||
- **Agent-native**: built for coding agents with tool use, sessions, memory, and multi-agent routing
|
||||
- **Open source**: MIT licensed, community-driven
|
||||
|
||||
**What do you need?** Node 22+, an API key (Anthropic recommended), and 5 minutes.
|
||||
|
||||
## How it works
|
||||
|
||||
```mermaid
|
||||
flowchart LR
|
||||
A["Chat apps + plugins"] --> B["Gateway"]
|
||||
B --> C["Pi agent"]
|
||||
B --> D["CLI"]
|
||||
B --> E["Web Control UI"]
|
||||
B --> F["macOS app"]
|
||||
B --> G["iOS and Android nodes"]
|
||||
```
|
||||
|
||||
The Gateway is the single source of truth for sessions, routing, and channel connections.
|
||||
|
||||
## Key capabilities
|
||||
|
||||
<Columns>
|
||||
<Card title="Multi-channel gateway" icon="network">
|
||||
WhatsApp, Telegram, Discord, and iMessage with a single Gateway process.
|
||||
</Card>
|
||||
<Card title="Plugin channels" icon="plug">
|
||||
Add Mattermost and more with extension packages.
|
||||
</Card>
|
||||
<Card title="Multi-agent routing" icon="route">
|
||||
Isolated sessions per agent, workspace, or sender.
|
||||
</Card>
|
||||
<Card title="Media support" icon="image">
|
||||
Send and receive images, audio, and documents.
|
||||
</Card>
|
||||
<Card title="Web Control UI" icon="monitor">
|
||||
Browser dashboard for chat, config, sessions, and nodes.
|
||||
</Card>
|
||||
<Card title="Mobile nodes" icon="smartphone">
|
||||
Pair iOS and Android nodes with Canvas support.
|
||||
</Card>
|
||||
</Columns>
|
||||
|
||||
## Quick start
|
||||
|
||||
<Steps>
|
||||
<Step title="Install OpenClaw">
|
||||
```bash
|
||||
npm install -g openclaw@latest
|
||||
```
|
||||
</Step>
|
||||
<Step title="Onboard and install the service">
|
||||
```bash
|
||||
openclaw onboard --install-daemon
|
||||
```
|
||||
</Step>
|
||||
<Step title="Pair WhatsApp and start the Gateway">
|
||||
```bash
|
||||
openclaw channels login
|
||||
openclaw gateway --port 18789
|
||||
```
|
||||
</Step>
|
||||
</Steps>
|
||||
|
||||
Need the full install and dev setup? See [Quick start](/start/quickstart).
|
||||
|
||||
## Dashboard
|
||||
|
||||
Open the browser Control UI after the Gateway starts.
|
||||
|
||||
- Local default: http://127.0.0.1:18789/
|
||||
- Remote access: [Web surfaces](/web) and [Tailscale](/gateway/tailscale)
|
||||
|
||||
<p align="center">
|
||||
<img src="whatsapp-openclaw.jpg" alt="OpenClaw" width="420" />
|
||||
</p>
|
||||
|
||||
## How it works
|
||||
|
||||
```
|
||||
WhatsApp / Telegram / Discord / iMessage (+ plugins)
|
||||
│
|
||||
▼
|
||||
┌───────────────────────────┐
|
||||
│ Gateway │ ws://127.0.0.1:18789 (loopback-only)
|
||||
│ (single source) │
|
||||
│ │ http://<gateway-host>:18793
|
||||
│ │ /__openclaw__/canvas/ (Canvas host)
|
||||
└───────────┬───────────────┘
|
||||
│
|
||||
├─ Pi agent (RPC)
|
||||
├─ CLI (openclaw …)
|
||||
├─ Chat UI (SwiftUI)
|
||||
├─ macOS app (OpenClaw.app)
|
||||
├─ iOS node via Gateway WS + pairing
|
||||
└─ Android node via Gateway WS + pairing
|
||||
```
|
||||
|
||||
Most operations flow through the **Gateway** (`openclaw gateway`), a single long-running process that owns channel connections and the WebSocket control plane.
|
||||
|
||||
## Network model
|
||||
|
||||
- **One Gateway per host (recommended)**: it is the only process allowed to own the WhatsApp Web session. If you need a rescue bot or strict isolation, run multiple gateways with isolated profiles and ports; see [Multiple gateways](/gateway/multiple-gateways).
|
||||
- **Loopback-first**: Gateway WS defaults to `ws://127.0.0.1:18789`.
|
||||
- The wizard now generates a gateway token by default (even for loopback).
|
||||
- For Tailnet access, run `openclaw gateway --bind tailnet --token ...` (token is required for non-loopback binds).
|
||||
- **Nodes**: connect to the Gateway WebSocket (LAN/tailnet/SSH as needed); legacy TCP bridge is deprecated/removed.
|
||||
- **Canvas host**: HTTP file server on `canvasHost.port` (default `18793`), serving `/__openclaw__/canvas/` for node WebViews; see [Gateway configuration](/gateway/configuration) (`canvasHost`).
|
||||
- **Remote use**: SSH tunnel or tailnet/VPN; see [Remote access](/gateway/remote) and [Discovery](/gateway/discovery).
|
||||
|
||||
## Features (high level)
|
||||
|
||||
- 📱 **WhatsApp Integration** — Uses Baileys for WhatsApp Web protocol
|
||||
- ✈️ **Telegram Bot** — DMs + groups via grammY
|
||||
- 🎮 **Discord Bot** — DMs + guild channels via channels.discord.js
|
||||
- 🧩 **Mattermost Bot (plugin)** — Bot token + WebSocket events
|
||||
- 💬 **iMessage** — Local imsg CLI integration (macOS)
|
||||
- 🤖 **Agent bridge** — Pi (RPC mode) with tool streaming
|
||||
- ⏱️ **Streaming + chunking** — Block streaming + Telegram draft streaming details ([/concepts/streaming](/concepts/streaming))
|
||||
- 🧠 **Multi-agent routing** — Route provider accounts/peers to isolated agents (workspace + per-agent sessions)
|
||||
- 🔐 **Subscription auth** — Anthropic (Claude Pro/Max) + OpenAI (ChatGPT/Codex) via OAuth
|
||||
- 💬 **Sessions** — Direct chats collapse into shared `main` (default); groups are isolated
|
||||
- 👥 **Group Chat Support** — Mention-based by default; owner can toggle `/activation always|mention`
|
||||
- 📎 **Media Support** — Send and receive images, audio, documents
|
||||
- 🎤 **Voice notes** — Optional transcription hook
|
||||
- 🖥️ **WebChat + macOS app** — Local UI + menu bar companion for ops and voice wake
|
||||
- 📱 **iOS node** — Pairs as a node and exposes a Canvas surface
|
||||
- 📱 **Android node** — Pairs as a node and exposes Canvas + Chat + Camera
|
||||
|
||||
Note: legacy Claude/Codex/Gemini/Opencode paths have been removed; Pi is the only coding-agent path.
|
||||
|
||||
## Quick start
|
||||
|
||||
Runtime requirement: **Node ≥ 22**.
|
||||
|
||||
```bash
|
||||
# Recommended: global install (npm/pnpm)
|
||||
npm install -g openclaw@latest
|
||||
# or: pnpm add -g openclaw@latest
|
||||
|
||||
# Onboard + install the service (launchd/systemd user service)
|
||||
openclaw onboard --install-daemon
|
||||
|
||||
# Pair WhatsApp Web (shows QR)
|
||||
openclaw channels login
|
||||
|
||||
# Gateway runs via the service after onboarding; manual run is still possible:
|
||||
openclaw gateway --port 18789
|
||||
```
|
||||
|
||||
Switching between npm and git installs later is easy: install the other flavor and run `openclaw doctor` to update the gateway service entrypoint.
|
||||
|
||||
From source (development):
|
||||
|
||||
```bash
|
||||
git clone https://github.com/openclaw/openclaw.git
|
||||
cd openclaw
|
||||
pnpm install
|
||||
pnpm ui:build # auto-installs UI deps on first run
|
||||
pnpm build
|
||||
openclaw onboard --install-daemon
|
||||
```
|
||||
|
||||
If you don’t have a global install yet, run the onboarding step via `pnpm openclaw ...` from the repo.
|
||||
|
||||
Multi-instance quickstart (optional):
|
||||
|
||||
```bash
|
||||
OPENCLAW_CONFIG_PATH=~/.openclaw/a.json \
|
||||
OPENCLAW_STATE_DIR=~/.openclaw-a \
|
||||
openclaw gateway --port 19001
|
||||
```
|
||||
|
||||
Send a test message (requires a running Gateway):
|
||||
|
||||
```bash
|
||||
openclaw message send --target +15555550123 --message "Hello from OpenClaw"
|
||||
```
|
||||
|
||||
## Configuration (optional)
|
||||
|
||||
Config lives at `~/.openclaw/openclaw.json`.
|
||||
@@ -182,77 +148,45 @@ Example:
|
||||
}
|
||||
```
|
||||
|
||||
## Docs
|
||||
## Start here
|
||||
|
||||
- Start here:
|
||||
- [Docs hubs (all pages linked)](/start/hubs)
|
||||
- [Help](/help) ← _common fixes + troubleshooting_
|
||||
- [Configuration](/gateway/configuration)
|
||||
- [Configuration examples](/gateway/configuration-examples)
|
||||
- [Slash commands](/tools/slash-commands)
|
||||
- [Multi-agent routing](/concepts/multi-agent)
|
||||
- [Updating / rollback](/install/updating)
|
||||
- [Pairing (DM + nodes)](/start/pairing)
|
||||
- [Nix mode](/install/nix)
|
||||
- [OpenClaw assistant setup](/start/openclaw)
|
||||
- [Skills](/tools/skills)
|
||||
- [Skills config](/tools/skills-config)
|
||||
- [Workspace templates](/reference/templates/AGENTS)
|
||||
- [RPC adapters](/reference/rpc)
|
||||
- [Gateway runbook](/gateway)
|
||||
- [Nodes (iOS/Android)](/nodes)
|
||||
- [Web surfaces (Control UI)](/web)
|
||||
- [Discovery + transports](/gateway/discovery)
|
||||
- [Remote access](/gateway/remote)
|
||||
- Providers and UX:
|
||||
- [WebChat](/web/webchat)
|
||||
- [Control UI (browser)](/web/control-ui)
|
||||
- [Telegram](/channels/telegram)
|
||||
- [Discord](/channels/discord)
|
||||
- [Mattermost (plugin)](/channels/mattermost)
|
||||
- [BlueBubbles (iMessage)](/channels/bluebubbles)
|
||||
- [iMessage (legacy)](/channels/imessage)
|
||||
- [Groups](/concepts/groups)
|
||||
- [WhatsApp group messages](/concepts/group-messages)
|
||||
- [Media: images](/nodes/images)
|
||||
- [Media: audio](/nodes/audio)
|
||||
- Companion apps:
|
||||
- [macOS app](/platforms/macos)
|
||||
- [iOS app](/platforms/ios)
|
||||
- [Android app](/platforms/android)
|
||||
- [Windows (WSL2)](/platforms/windows)
|
||||
- [Linux app](/platforms/linux)
|
||||
- Ops and safety:
|
||||
- [Sessions](/concepts/session)
|
||||
- [Cron jobs](/automation/cron-jobs)
|
||||
- [Webhooks](/automation/webhook)
|
||||
- [Gmail hooks (Pub/Sub)](/automation/gmail-pubsub)
|
||||
- [Security](/gateway/security)
|
||||
- [Troubleshooting](/gateway/troubleshooting)
|
||||
<Columns>
|
||||
<Card title="Docs hubs" href="/start/hubs" icon="book-open">
|
||||
All docs and guides, organized by use case.
|
||||
</Card>
|
||||
<Card title="Configuration" href="/gateway/configuration" icon="settings">
|
||||
Core Gateway settings, tokens, and provider config.
|
||||
</Card>
|
||||
<Card title="Remote access" href="/gateway/remote" icon="globe">
|
||||
SSH and tailnet access patterns.
|
||||
</Card>
|
||||
<Card title="Channels" href="/channels/telegram" icon="message-square">
|
||||
Channel-specific setup for WhatsApp, Telegram, Discord, and more.
|
||||
</Card>
|
||||
<Card title="Nodes" href="/nodes" icon="smartphone">
|
||||
iOS and Android nodes with pairing and Canvas.
|
||||
</Card>
|
||||
<Card title="Help" href="/help" icon="life-buoy">
|
||||
Common fixes and troubleshooting entry point.
|
||||
</Card>
|
||||
</Columns>
|
||||
|
||||
## The name
|
||||
## Learn more
|
||||
|
||||
**OpenClaw = CLAW + TARDIS** — because every space lobster needs a time-and-space machine.
|
||||
|
||||
---
|
||||
|
||||
_"We're all just playing with our own prompts."_ — an AI, probably high on tokens
|
||||
|
||||
## Credits
|
||||
|
||||
- **Peter Steinberger** ([@steipete](https://x.com/steipete)) — Creator, lobster whisperer
|
||||
- **Mario Zechner** ([@badlogicc](https://x.com/badlogicgames)) — Pi creator, security pen-tester
|
||||
- **Clawd** — The space lobster who demanded a better name
|
||||
|
||||
## Core Contributors
|
||||
|
||||
- **Maxim Vovshin** (@Hyaxia, 36747317+Hyaxia@users.noreply.github.com) — Blogwatcher skill
|
||||
- **Nacho Iacovino** (@nachoiacovino, nacho.iacovino@gmail.com) — Location parsing (Telegram + WhatsApp)
|
||||
|
||||
## License
|
||||
|
||||
MIT — Free as a lobster in the ocean 🦞
|
||||
|
||||
---
|
||||
|
||||
_"We're all just playing with our own prompts."_ — An AI, probably high on tokens
|
||||
<Columns>
|
||||
<Card title="Full feature list" href="/concepts/features" icon="list">
|
||||
Complete channel, routing, and media capabilities.
|
||||
</Card>
|
||||
<Card title="Multi-agent routing" href="/concepts/multi-agent" icon="route">
|
||||
Workspace isolation and per-agent sessions.
|
||||
</Card>
|
||||
<Card title="Security" href="/gateway/security" icon="shield">
|
||||
Tokens, allowlists, and safety controls.
|
||||
</Card>
|
||||
<Card title="Troubleshooting" href="/gateway/troubleshooting" icon="wrench">
|
||||
Gateway diagnostics and common errors.
|
||||
</Card>
|
||||
<Card title="About and credits" href="/reference/credits" icon="info">
|
||||
Project origins, contributors, and license.
|
||||
</Card>
|
||||
</Columns>
|
||||
|
||||
@@ -63,7 +63,7 @@ It writes config/workspace on the host:
|
||||
- `~/.openclaw/`
|
||||
- `~/.openclaw/workspace`
|
||||
|
||||
Running on a VPS? See [Hetzner (Docker VPS)](/platforms/hetzner).
|
||||
Running on a VPS? See [Hetzner (Docker VPS)](/install/hetzner).
|
||||
|
||||
### Manual flow (compose)
|
||||
|
||||
|
||||
@@ -148,7 +148,7 @@ cat > /data/openclaw.json << 'EOF'
|
||||
"agents": {
|
||||
"defaults": {
|
||||
"model": {
|
||||
"primary": "anthropic/claude-opus-4-5",
|
||||
"primary": "anthropic/claude-opus-4-6",
|
||||
"fallbacks": ["anthropic/claude-sonnet-4-5", "openai/gpt-4o"]
|
||||
},
|
||||
"maxConcurrent": 4
|
||||
@@ -3,10 +3,10 @@ summary: "Install OpenClaw (recommended installer, global install, or from sourc
|
||||
read_when:
|
||||
- Installing OpenClaw
|
||||
- You want to install from GitHub
|
||||
title: "Install"
|
||||
title: "Install Overview"
|
||||
---
|
||||
|
||||
# Install
|
||||
# Install Overview
|
||||
|
||||
Use the installer unless you have a reason not to. It sets up the CLI and runs onboarding.
|
||||
|
||||
@@ -102,6 +102,8 @@ openclaw onboard --install-daemon
|
||||
|
||||
Tip: if you don’t have a global install yet, run repo commands via `pnpm openclaw ...`.
|
||||
|
||||
For deeper development workflows, see [Setup](/start/setup).
|
||||
|
||||
### 4) Other install options
|
||||
|
||||
- Docker: [Docker](/install/docker)
|
||||
|
||||
@@ -186,7 +186,7 @@ If you omit `capabilities`, the entry is eligible for the list it appears in.
|
||||
**Image**
|
||||
|
||||
- Prefer your active model if it supports images.
|
||||
- Good defaults: `openai/gpt-5.2`, `anthropic/claude-opus-4-5`, `google/gemini-3-pro-preview`.
|
||||
- Good defaults: `openai/gpt-5.2`, `anthropic/claude-opus-4-6`, `google/gemini-3-pro-preview`.
|
||||
|
||||
**Audio**
|
||||
|
||||
@@ -300,7 +300,7 @@ When `mode: "all"`, outputs are labeled `[Image 1/2]`, `[Audio 2/2]`, etc.
|
||||
maxChars: 500,
|
||||
models: [
|
||||
{ provider: "openai", model: "gpt-5.2" },
|
||||
{ provider: "anthropic", model: "claude-opus-4-5" },
|
||||
{ provider: "anthropic", model: "claude-opus-4-6" },
|
||||
{
|
||||
type: "cli",
|
||||
command: "gemini",
|
||||
|
||||
@@ -27,7 +27,7 @@ If you want a $0/month option and don’t mind ARM + provider-specific setup, se
|
||||
**Picking a provider:**
|
||||
|
||||
- DigitalOcean: simplest UX + predictable setup (this guide)
|
||||
- Hetzner: good price/perf (see [Hetzner guide](/platforms/hetzner))
|
||||
- Hetzner: good price/perf (see [Hetzner guide](/install/hetzner))
|
||||
- Oracle Cloud: can be $0/month, but is more finicky and ARM-only (see [Oracle guide](/platforms/oracle))
|
||||
|
||||
---
|
||||
@@ -256,7 +256,7 @@ free -h
|
||||
|
||||
## See Also
|
||||
|
||||
- [Hetzner guide](/platforms/hetzner) — cheaper, more powerful
|
||||
- [Hetzner guide](/install/hetzner) — cheaper, more powerful
|
||||
- [Docker install](/install/docker) — containerized setup
|
||||
- [Tailscale](/gateway/tailscale) — secure remote access
|
||||
- [Configuration](/gateway/configuration) — full config reference
|
||||
|
||||
@@ -26,10 +26,10 @@ Native companion apps for Windows are also planned; the Gateway is recommended v
|
||||
## VPS & hosting
|
||||
|
||||
- VPS hub: [VPS hosting](/vps)
|
||||
- Fly.io: [Fly.io](/platforms/fly)
|
||||
- Hetzner (Docker): [Hetzner](/platforms/hetzner)
|
||||
- GCP (Compute Engine): [GCP](/platforms/gcp)
|
||||
- exe.dev (VM + HTTPS proxy): [exe.dev](/platforms/exe-dev)
|
||||
- Fly.io: [Fly.io](/install/fly)
|
||||
- Hetzner (Docker): [Hetzner](/install/hetzner)
|
||||
- GCP (Compute Engine): [GCP](/install/gcp)
|
||||
- exe.dev (VM + HTTPS proxy): [exe.dev](/install/exe-dev)
|
||||
|
||||
## Common links
|
||||
|
||||
|
||||
@@ -21,7 +21,7 @@ Native Linux companion apps are planned. Contributions are welcome if you want t
|
||||
4. From your laptop: `ssh -N -L 18789:127.0.0.1:18789 <user>@<host>`
|
||||
5. Open `http://127.0.0.1:18789/` and paste your token
|
||||
|
||||
Step-by-step VPS guide: [exe.dev](/platforms/exe-dev)
|
||||
Step-by-step VPS guide: [exe.dev](/install/exe-dev)
|
||||
|
||||
## Install
|
||||
|
||||
|
||||
@@ -34,17 +34,17 @@ Notes:
|
||||
# From repo root; set release IDs so Sparkle feed is enabled.
|
||||
# APP_BUILD must be numeric + monotonic for Sparkle compare.
|
||||
BUNDLE_ID=bot.molt.mac \
|
||||
APP_VERSION=2026.2.3 \
|
||||
APP_VERSION=2026.2.4 \
|
||||
APP_BUILD="$(git rev-list --count HEAD)" \
|
||||
BUILD_CONFIG=release \
|
||||
SIGN_IDENTITY="Developer ID Application: <Developer Name> (<TEAMID>)" \
|
||||
scripts/package-mac-app.sh
|
||||
|
||||
# Zip for distribution (includes resource forks for Sparkle delta support)
|
||||
ditto -c -k --sequesterRsrc --keepParent dist/OpenClaw.app dist/OpenClaw-2026.2.3.zip
|
||||
ditto -c -k --sequesterRsrc --keepParent dist/OpenClaw.app dist/OpenClaw-2026.2.4.zip
|
||||
|
||||
# Optional: also build a styled DMG for humans (drag to /Applications)
|
||||
scripts/create-dmg.sh dist/OpenClaw.app dist/OpenClaw-2026.2.3.dmg
|
||||
scripts/create-dmg.sh dist/OpenClaw.app dist/OpenClaw-2026.2.4.dmg
|
||||
|
||||
# Recommended: build + notarize/staple zip + DMG
|
||||
# First, create a keychain profile once:
|
||||
@@ -52,14 +52,14 @@ scripts/create-dmg.sh dist/OpenClaw.app dist/OpenClaw-2026.2.3.dmg
|
||||
# --apple-id "<apple-id>" --team-id "<team-id>" --password "<app-specific-password>"
|
||||
NOTARIZE=1 NOTARYTOOL_PROFILE=openclaw-notary \
|
||||
BUNDLE_ID=bot.molt.mac \
|
||||
APP_VERSION=2026.2.3 \
|
||||
APP_VERSION=2026.2.4 \
|
||||
APP_BUILD="$(git rev-list --count HEAD)" \
|
||||
BUILD_CONFIG=release \
|
||||
SIGN_IDENTITY="Developer ID Application: <Developer Name> (<TEAMID>)" \
|
||||
scripts/package-mac-dist.sh
|
||||
|
||||
# Optional: ship dSYM alongside the release
|
||||
ditto -c -k --keepParent apps/macos/.build/release/OpenClaw.app.dSYM dist/OpenClaw-2026.2.3.dSYM.zip
|
||||
ditto -c -k --keepParent apps/macos/.build/release/OpenClaw.app.dSYM dist/OpenClaw-2026.2.4.dSYM.zip
|
||||
```
|
||||
|
||||
## Appcast entry
|
||||
@@ -67,7 +67,7 @@ ditto -c -k --keepParent apps/macos/.build/release/OpenClaw.app.dSYM dist/OpenCl
|
||||
Use the release note generator so Sparkle renders formatted HTML notes:
|
||||
|
||||
```bash
|
||||
SPARKLE_PRIVATE_KEY_FILE=/path/to/ed25519-private-key scripts/make_appcast.sh dist/OpenClaw-2026.2.3.zip https://raw.githubusercontent.com/openclaw/openclaw/main/appcast.xml
|
||||
SPARKLE_PRIVATE_KEY_FILE=/path/to/ed25519-private-key scripts/make_appcast.sh dist/OpenClaw-2026.2.4.zip https://raw.githubusercontent.com/openclaw/openclaw/main/appcast.xml
|
||||
```
|
||||
|
||||
Generates HTML release notes from `CHANGELOG.md` (via [`scripts/changelog-to-html.sh`](https://github.com/openclaw/openclaw/blob/main/scripts/changelog-to-html.sh)) and embeds them in the appcast entry.
|
||||
@@ -75,7 +75,7 @@ Commit the updated `appcast.xml` alongside the release assets (zip + dSYM) when
|
||||
|
||||
## Publish & verify
|
||||
|
||||
- Upload `OpenClaw-2026.2.3.zip` (and `OpenClaw-2026.2.3.dSYM.zip`) to the GitHub release for tag `v2026.2.3`.
|
||||
- Upload `OpenClaw-2026.2.4.zip` (and `OpenClaw-2026.2.4.dSYM.zip`) to the GitHub release for tag `v2026.2.4`.
|
||||
- Ensure the raw appcast URL matches the baked feed: `https://raw.githubusercontent.com/openclaw/openclaw/main/appcast.xml`.
|
||||
- Sanity checks:
|
||||
- `curl -I https://raw.githubusercontent.com/openclaw/openclaw/main/appcast.xml` returns 200.
|
||||
|
||||
@@ -300,4 +300,4 @@ tar -czvf openclaw-backup.tar.gz ~/.openclaw ~/.openclaw/workspace
|
||||
- [Tailscale integration](/gateway/tailscale) — full Tailscale docs
|
||||
- [Gateway configuration](/gateway/configuration) — all config options
|
||||
- [DigitalOcean guide](/platforms/digitalocean) — if you want paid + easier signup
|
||||
- [Hetzner guide](/platforms/hetzner) — Docker-based alternative
|
||||
- [Hetzner guide](/install/hetzner) — Docker-based alternative
|
||||
|
||||
@@ -353,6 +353,6 @@ echo 'wireless-power off' | sudo tee -a /etc/network/interfaces
|
||||
|
||||
- [Linux guide](/platforms/linux) — general Linux setup
|
||||
- [DigitalOcean guide](/platforms/digitalocean) — cloud alternative
|
||||
- [Hetzner guide](/platforms/hetzner) — Docker setup
|
||||
- [Hetzner guide](/install/hetzner) — Docker setup
|
||||
- [Tailscale](/gateway/tailscale) — remote access
|
||||
- [Nodes](/nodes) — pair your laptop/phone with the Pi gateway
|
||||
|
||||
@@ -31,7 +31,7 @@ openclaw onboard --anthropic-api-key "$ANTHROPIC_API_KEY"
|
||||
```json5
|
||||
{
|
||||
env: { ANTHROPIC_API_KEY: "sk-ant-..." },
|
||||
agents: { defaults: { model: { primary: "anthropic/claude-opus-4-5" } } },
|
||||
agents: { defaults: { model: { primary: "anthropic/claude-opus-4-6" } } },
|
||||
}
|
||||
```
|
||||
|
||||
@@ -54,7 +54,7 @@ Use the `cacheRetention` parameter in your model config:
|
||||
agents: {
|
||||
defaults: {
|
||||
models: {
|
||||
"anthropic/claude-opus-4-5": {
|
||||
"anthropic/claude-opus-4-6": {
|
||||
params: { cacheRetention: "long" },
|
||||
},
|
||||
},
|
||||
@@ -114,7 +114,7 @@ openclaw onboard --auth-choice setup-token
|
||||
|
||||
```json5
|
||||
{
|
||||
agents: { defaults: { model: { primary: "anthropic/claude-opus-4-5" } } },
|
||||
agents: { defaults: { model: { primary: "anthropic/claude-opus-4-6" } } },
|
||||
}
|
||||
```
|
||||
|
||||
|
||||
71
docs/providers/cloudflare-ai-gateway.md
Normal file
71
docs/providers/cloudflare-ai-gateway.md
Normal file
@@ -0,0 +1,71 @@
|
||||
---
|
||||
title: "Cloudflare AI Gateway"
|
||||
summary: "Cloudflare AI Gateway setup (auth + model selection)"
|
||||
read_when:
|
||||
- You want to use Cloudflare AI Gateway with OpenClaw
|
||||
- You need the account ID, gateway ID, or API key env var
|
||||
---
|
||||
|
||||
# Cloudflare AI Gateway
|
||||
|
||||
Cloudflare AI Gateway sits in front of provider APIs and lets you add analytics, caching, and controls. For Anthropic, OpenClaw uses the Anthropic Messages API through your Gateway endpoint.
|
||||
|
||||
- Provider: `cloudflare-ai-gateway`
|
||||
- Base URL: `https://gateway.ai.cloudflare.com/v1/<account_id>/<gateway_id>/anthropic`
|
||||
- Default model: `cloudflare-ai-gateway/claude-sonnet-4-5`
|
||||
- API key: `CLOUDFLARE_AI_GATEWAY_API_KEY` (your provider API key for requests through the Gateway)
|
||||
|
||||
For Anthropic models, use your Anthropic API key.
|
||||
|
||||
## Quick start
|
||||
|
||||
1. Set the provider API key and Gateway details:
|
||||
|
||||
```bash
|
||||
openclaw onboard --auth-choice cloudflare-ai-gateway-api-key
|
||||
```
|
||||
|
||||
2. Set a default model:
|
||||
|
||||
```json5
|
||||
{
|
||||
agents: {
|
||||
defaults: {
|
||||
model: { primary: "cloudflare-ai-gateway/claude-sonnet-4-5" },
|
||||
},
|
||||
},
|
||||
}
|
||||
```
|
||||
|
||||
## Non-interactive example
|
||||
|
||||
```bash
|
||||
openclaw onboard --non-interactive \
|
||||
--mode local \
|
||||
--auth-choice cloudflare-ai-gateway-api-key \
|
||||
--cloudflare-ai-gateway-account-id "your-account-id" \
|
||||
--cloudflare-ai-gateway-gateway-id "your-gateway-id" \
|
||||
--cloudflare-ai-gateway-api-key "$CLOUDFLARE_AI_GATEWAY_API_KEY"
|
||||
```
|
||||
|
||||
## Authenticated gateways
|
||||
|
||||
If you enabled Gateway authentication in Cloudflare, add the `cf-aig-authorization` header (this is in addition to your provider API key).
|
||||
|
||||
```json5
|
||||
{
|
||||
models: {
|
||||
providers: {
|
||||
"cloudflare-ai-gateway": {
|
||||
headers: {
|
||||
"cf-aig-authorization": "Bearer <cloudflare-ai-gateway-token>",
|
||||
},
|
||||
},
|
||||
},
|
||||
},
|
||||
}
|
||||
```
|
||||
|
||||
## Environment note
|
||||
|
||||
If the Gateway runs as a daemon (launchd/systemd), make sure `CLOUDFLARE_AI_GATEWAY_API_KEY` is available to that process (for example, in `~/.openclaw/.env` or via `env.shellEnv`).
|
||||
@@ -29,7 +29,7 @@ See [Venice AI](/providers/venice).
|
||||
|
||||
```json5
|
||||
{
|
||||
agents: { defaults: { model: { primary: "anthropic/claude-opus-4-5" } } },
|
||||
agents: { defaults: { model: { primary: "anthropic/claude-opus-4-6" } } },
|
||||
}
|
||||
```
|
||||
|
||||
@@ -40,6 +40,7 @@ See [Venice AI](/providers/venice).
|
||||
- [Qwen (OAuth)](/providers/qwen)
|
||||
- [OpenRouter](/providers/openrouter)
|
||||
- [Vercel AI Gateway](/providers/vercel-ai-gateway)
|
||||
- [Cloudflare AI Gateway](/providers/cloudflare-ai-gateway)
|
||||
- [Moonshot AI (Kimi + Kimi Coding)](/providers/moonshot)
|
||||
- [OpenCode Zen](/providers/opencode)
|
||||
- [Amazon Bedrock](/bedrock)
|
||||
|
||||
@@ -96,7 +96,7 @@ Configure via CLI:
|
||||
|
||||
### MiniMax M2.1 as fallback (Opus primary)
|
||||
|
||||
**Best for:** keep Opus 4.5 as primary, fail over to MiniMax M2.1.
|
||||
**Best for:** keep Opus 4.6 as primary, fail over to MiniMax M2.1.
|
||||
|
||||
```json5
|
||||
{
|
||||
@@ -104,11 +104,11 @@ Configure via CLI:
|
||||
agents: {
|
||||
defaults: {
|
||||
models: {
|
||||
"anthropic/claude-opus-4-5": { alias: "opus" },
|
||||
"anthropic/claude-opus-4-6": { alias: "opus" },
|
||||
"minimax/MiniMax-M2.1": { alias: "minimax" },
|
||||
},
|
||||
model: {
|
||||
primary: "anthropic/claude-opus-4-5",
|
||||
primary: "anthropic/claude-opus-4-6",
|
||||
fallbacks: ["minimax/MiniMax-M2.1"],
|
||||
},
|
||||
},
|
||||
|
||||
@@ -27,7 +27,7 @@ See [Venice AI](/providers/venice).
|
||||
|
||||
```json5
|
||||
{
|
||||
agents: { defaults: { model: { primary: "anthropic/claude-opus-4-5" } } },
|
||||
agents: { defaults: { model: { primary: "anthropic/claude-opus-4-6" } } },
|
||||
}
|
||||
```
|
||||
|
||||
@@ -37,6 +37,7 @@ See [Venice AI](/providers/venice).
|
||||
- [Anthropic (API + Claude Code CLI)](/providers/anthropic)
|
||||
- [OpenRouter](/providers/openrouter)
|
||||
- [Vercel AI Gateway](/providers/vercel-ai-gateway)
|
||||
- [Cloudflare AI Gateway](/providers/cloudflare-ai-gateway)
|
||||
- [Moonshot AI (Kimi + Kimi Coding)](/providers/moonshot)
|
||||
- [Synthetic](/providers/synthetic)
|
||||
- [OpenCode Zen](/providers/opencode)
|
||||
|
||||
@@ -17,6 +17,8 @@ Ollama is a local LLM runtime that makes it easy to run open-source models on yo
|
||||
2. Pull a model:
|
||||
|
||||
```bash
|
||||
ollama pull gpt-oss:20b
|
||||
# or
|
||||
ollama pull llama3.3
|
||||
# or
|
||||
ollama pull qwen2.5-coder:32b
|
||||
@@ -40,7 +42,7 @@ openclaw config set models.providers.ollama.apiKey "ollama-local"
|
||||
{
|
||||
agents: {
|
||||
defaults: {
|
||||
model: { primary: "ollama/llama3.3" },
|
||||
model: { primary: "ollama/gpt-oss:20b" },
|
||||
},
|
||||
},
|
||||
}
|
||||
@@ -105,8 +107,8 @@ Use explicit config when:
|
||||
api: "openai-completions",
|
||||
models: [
|
||||
{
|
||||
id: "llama3.3",
|
||||
name: "Llama 3.3",
|
||||
id: "gpt-oss:20b",
|
||||
name: "GPT-OSS 20B",
|
||||
reasoning: false,
|
||||
input: ["text"],
|
||||
cost: { input: 0, output: 0, cacheRead: 0, cacheWrite: 0 },
|
||||
@@ -148,8 +150,8 @@ Once configured, all your Ollama models are available:
|
||||
agents: {
|
||||
defaults: {
|
||||
model: {
|
||||
primary: "ollama/llama3.3",
|
||||
fallback: ["ollama/qwen2.5-coder:32b"],
|
||||
primary: "ollama/gpt-oss:20b",
|
||||
fallbacks: ["ollama/llama3.3", "ollama/qwen2.5-coder:32b"],
|
||||
},
|
||||
},
|
||||
},
|
||||
@@ -170,6 +172,48 @@ ollama pull deepseek-r1:32b
|
||||
|
||||
Ollama is free and runs locally, so all model costs are set to $0.
|
||||
|
||||
### Streaming Configuration
|
||||
|
||||
Due to a [known issue](https://github.com/badlogic/pi-mono/issues/1205) in the underlying SDK with Ollama's response format, **streaming is disabled by default** for Ollama models. This prevents corrupted responses when using tool-capable models.
|
||||
|
||||
When streaming is disabled, responses are delivered all at once (non-streaming mode), which avoids the issue where interleaved content/reasoning deltas cause garbled output.
|
||||
|
||||
#### Re-enable Streaming (Advanced)
|
||||
|
||||
If you want to re-enable streaming for Ollama (may cause issues with tool-capable models):
|
||||
|
||||
```json5
|
||||
{
|
||||
agents: {
|
||||
defaults: {
|
||||
models: {
|
||||
"ollama/gpt-oss:20b": {
|
||||
streaming: true,
|
||||
},
|
||||
},
|
||||
},
|
||||
},
|
||||
}
|
||||
```
|
||||
|
||||
#### Disable Streaming for Other Providers
|
||||
|
||||
You can also disable streaming for any provider if needed:
|
||||
|
||||
```json5
|
||||
{
|
||||
agents: {
|
||||
defaults: {
|
||||
models: {
|
||||
"openai/gpt-4": {
|
||||
streaming: false,
|
||||
},
|
||||
},
|
||||
},
|
||||
},
|
||||
}
|
||||
```
|
||||
|
||||
### Context windows
|
||||
|
||||
For auto-discovered models, OpenClaw uses the context window reported by Ollama when available, otherwise it defaults to `8192`. You can override `contextWindow` and `maxTokens` in explicit provider config.
|
||||
@@ -201,7 +245,8 @@ To add models:
|
||||
|
||||
```bash
|
||||
ollama list # See what's installed
|
||||
ollama pull llama3.3 # Pull a model
|
||||
ollama pull gpt-oss:20b # Pull a tool-capable model
|
||||
ollama pull llama3.3 # Or another model
|
||||
```
|
||||
|
||||
### Connection refused
|
||||
@@ -216,6 +261,15 @@ ps aux | grep ollama
|
||||
ollama serve
|
||||
```
|
||||
|
||||
### Corrupted responses or tool names in output
|
||||
|
||||
If you see garbled responses containing tool names (like `sessions_send`, `memory_get`) or fragmented text when using Ollama models, this is due to an upstream SDK issue with streaming responses. **This is fixed by default** in the latest OpenClaw version by disabling streaming for Ollama models.
|
||||
|
||||
If you manually enabled streaming and experience this issue:
|
||||
|
||||
1. Remove the `streaming: true` configuration from your Ollama model entries, or
|
||||
2. Explicitly set `streaming: false` for Ollama models (see [Streaming Configuration](#streaming-configuration))
|
||||
|
||||
## See Also
|
||||
|
||||
- [Model Providers](/concepts/model-providers) - Overview of all providers
|
||||
|
||||
@@ -29,7 +29,7 @@ openclaw onboard --openai-api-key "$OPENAI_API_KEY"
|
||||
```json5
|
||||
{
|
||||
env: { OPENAI_API_KEY: "sk-..." },
|
||||
agents: { defaults: { model: { primary: "openai/gpt-5.2" } } },
|
||||
agents: { defaults: { model: { primary: "openai/gpt-5.1-codex" } } },
|
||||
}
|
||||
```
|
||||
|
||||
@@ -52,7 +52,7 @@ openclaw models auth login --provider openai-codex
|
||||
|
||||
```json5
|
||||
{
|
||||
agents: { defaults: { model: { primary: "openai-codex/gpt-5.2" } } },
|
||||
agents: { defaults: { model: { primary: "openai-codex/gpt-5.3-codex" } } },
|
||||
}
|
||||
```
|
||||
|
||||
|
||||
@@ -25,7 +25,7 @@ openclaw onboard --opencode-zen-api-key "$OPENCODE_API_KEY"
|
||||
```json5
|
||||
{
|
||||
env: { OPENCODE_API_KEY: "sk-..." },
|
||||
agents: { defaults: { model: { primary: "opencode/claude-opus-4-5" } } },
|
||||
agents: { defaults: { model: { primary: "opencode/claude-opus-4-6" } } },
|
||||
}
|
||||
```
|
||||
|
||||
|
||||
@@ -28,7 +28,7 @@ openclaw onboard --auth-choice ai-gateway-api-key
|
||||
{
|
||||
agents: {
|
||||
defaults: {
|
||||
model: { primary: "vercel-ai-gateway/anthropic/claude-opus-4.5" },
|
||||
model: { primary: "vercel-ai-gateway/anthropic/claude-opus-4.6" },
|
||||
},
|
||||
},
|
||||
}
|
||||
|
||||
27
docs/reference/credits.md
Normal file
27
docs/reference/credits.md
Normal file
@@ -0,0 +1,27 @@
|
||||
---
|
||||
summary: "Project origin, contributors, and license."
|
||||
read_when:
|
||||
- You want the project backstory or contributor credits
|
||||
title: "Credits"
|
||||
---
|
||||
|
||||
## The name
|
||||
|
||||
OpenClaw = CLAW + TARDIS, because every space lobster needs a time and space machine.
|
||||
|
||||
## Credits
|
||||
|
||||
- **Peter Steinberger** ([@steipete](https://x.com/steipete)) - Creator, lobster whisperer
|
||||
- **Mario Zechner** ([@badlogicc](https://x.com/badlogicgames)) - Pi creator, security pen tester
|
||||
- **Clawd** - The space lobster who demanded a better name
|
||||
|
||||
## Core contributors
|
||||
|
||||
- **Maxim Vovshin** (@Hyaxia, 36747317+Hyaxia@users.noreply.github.com) - Blogwatcher skill
|
||||
- **Nacho Iacovino** (@nachoiacovino, nacho.iacovino@gmail.com) - Location parsing (Telegram and WhatsApp)
|
||||
|
||||
## License
|
||||
|
||||
MIT - Free as a lobster in the ocean.
|
||||
|
||||
> "We are all just playing with our own prompts." (An AI, probably high on tokens)
|
||||
268
docs/reference/wizard.md
Normal file
268
docs/reference/wizard.md
Normal file
@@ -0,0 +1,268 @@
|
||||
---
|
||||
summary: "Full reference for the CLI onboarding wizard: every step, flag, and config field"
|
||||
read_when:
|
||||
- Looking up a specific wizard step or flag
|
||||
- Automating onboarding with non-interactive mode
|
||||
- Debugging wizard behavior
|
||||
title: "Onboarding Wizard Reference"
|
||||
sidebarTitle: "Wizard Reference"
|
||||
---
|
||||
|
||||
# Onboarding Wizard Reference
|
||||
|
||||
This is the full reference for the `openclaw onboard` CLI wizard.
|
||||
For a high-level overview, see [Onboarding Wizard](/start/wizard).
|
||||
|
||||
## Flow details (local mode)
|
||||
|
||||
<Steps>
|
||||
<Step title="Existing config detection">
|
||||
- If `~/.openclaw/openclaw.json` exists, choose **Keep / Modify / Reset**.
|
||||
- Re-running the wizard does **not** wipe anything unless you explicitly choose **Reset**
|
||||
(or pass `--reset`).
|
||||
- If the config is invalid or contains legacy keys, the wizard stops and asks
|
||||
you to run `openclaw doctor` before continuing.
|
||||
- Reset uses `trash` (never `rm`) and offers scopes:
|
||||
- Config only
|
||||
- Config + credentials + sessions
|
||||
- Full reset (also removes workspace)
|
||||
</Step>
|
||||
<Step title="Model/Auth">
|
||||
- **Anthropic API key (recommended)**: uses `ANTHROPIC_API_KEY` if present or prompts for a key, then saves it for daemon use.
|
||||
- **Anthropic OAuth (Claude Code CLI)**: on macOS the wizard checks Keychain item "Claude Code-credentials" (choose "Always Allow" so launchd starts don't block); on Linux/Windows it reuses `~/.claude/.credentials.json` if present.
|
||||
- **Anthropic token (paste setup-token)**: run `claude setup-token` on any machine, then paste the token (you can name it; blank = default).
|
||||
- **OpenAI Code (Codex) subscription (Codex CLI)**: if `~/.codex/auth.json` exists, the wizard can reuse it.
|
||||
- **OpenAI Code (Codex) subscription (OAuth)**: browser flow; paste the `code#state`.
|
||||
- Sets `agents.defaults.model` to `openai-codex/gpt-5.2` when model is unset or `openai/*`.
|
||||
- **OpenAI API key**: uses `OPENAI_API_KEY` if present or prompts for a key, then saves it to `~/.openclaw/.env` so launchd can read it.
|
||||
- **OpenCode Zen (multi-model proxy)**: prompts for `OPENCODE_API_KEY` (or `OPENCODE_ZEN_API_KEY`, get it at https://opencode.ai/auth).
|
||||
- **API key**: stores the key for you.
|
||||
- **Vercel AI Gateway (multi-model proxy)**: prompts for `AI_GATEWAY_API_KEY`.
|
||||
- More detail: [Vercel AI Gateway](/providers/vercel-ai-gateway)
|
||||
- **Cloudflare AI Gateway**: prompts for Account ID, Gateway ID, and `CLOUDFLARE_AI_GATEWAY_API_KEY`.
|
||||
- More detail: [Cloudflare AI Gateway](/providers/cloudflare-ai-gateway)
|
||||
- **MiniMax M2.1**: config is auto-written.
|
||||
- More detail: [MiniMax](/providers/minimax)
|
||||
- **Synthetic (Anthropic-compatible)**: prompts for `SYNTHETIC_API_KEY`.
|
||||
- More detail: [Synthetic](/providers/synthetic)
|
||||
- **Moonshot (Kimi K2)**: config is auto-written.
|
||||
- **Kimi Coding**: config is auto-written.
|
||||
- More detail: [Moonshot AI (Kimi + Kimi Coding)](/providers/moonshot)
|
||||
- **Skip**: no auth configured yet.
|
||||
- Pick a default model from detected options (or enter provider/model manually).
|
||||
- Wizard runs a model check and warns if the configured model is unknown or missing auth.
|
||||
- OAuth credentials live in `~/.openclaw/credentials/oauth.json`; auth profiles live in `~/.openclaw/agents/<agentId>/agent/auth-profiles.json` (API keys + OAuth).
|
||||
- More detail: [/concepts/oauth](/concepts/oauth)
|
||||
<Note>
|
||||
Headless/server tip: complete OAuth on a machine with a browser, then copy
|
||||
`~/.openclaw/credentials/oauth.json` (or `$OPENCLAW_STATE_DIR/credentials/oauth.json`) to the
|
||||
gateway host.
|
||||
</Note>
|
||||
</Step>
|
||||
<Step title="Workspace">
|
||||
- Default `~/.openclaw/workspace` (configurable).
|
||||
- Seeds the workspace files needed for the agent bootstrap ritual.
|
||||
- Full workspace layout + backup guide: [Agent workspace](/concepts/agent-workspace)
|
||||
</Step>
|
||||
<Step title="Gateway">
|
||||
- Port, bind, auth mode, tailscale exposure.
|
||||
- Auth recommendation: keep **Token** even for loopback so local WS clients must authenticate.
|
||||
- Disable auth only if you fully trust every local process.
|
||||
- Non‑loopback binds still require auth.
|
||||
</Step>
|
||||
<Step title="Channels">
|
||||
- [WhatsApp](/channels/whatsapp): optional QR login.
|
||||
- [Telegram](/channels/telegram): bot token.
|
||||
- [Discord](/channels/discord): bot token.
|
||||
- [Google Chat](/channels/googlechat): service account JSON + webhook audience.
|
||||
- [Mattermost](/channels/mattermost) (plugin): bot token + base URL.
|
||||
- [Signal](/channels/signal): optional `signal-cli` install + account config.
|
||||
- [BlueBubbles](/channels/bluebubbles): **recommended for iMessage**; server URL + password + webhook.
|
||||
- [iMessage](/channels/imessage): legacy `imsg` CLI path + DB access.
|
||||
- DM security: default is pairing. First DM sends a code; approve via `openclaw pairing approve <channel> <code>` or use allowlists.
|
||||
</Step>
|
||||
<Step title="Daemon install">
|
||||
- macOS: LaunchAgent
|
||||
- Requires a logged-in user session; for headless, use a custom LaunchDaemon (not shipped).
|
||||
- Linux (and Windows via WSL2): systemd user unit
|
||||
- Wizard attempts to enable lingering via `loginctl enable-linger <user>` so the Gateway stays up after logout.
|
||||
- May prompt for sudo (writes `/var/lib/systemd/linger`); it tries without sudo first.
|
||||
- **Runtime selection:** Node (recommended; required for WhatsApp/Telegram). Bun is **not recommended**.
|
||||
</Step>
|
||||
<Step title="Health check">
|
||||
- Starts the Gateway (if needed) and runs `openclaw health`.
|
||||
- Tip: `openclaw status --deep` adds gateway health probes to status output (requires a reachable gateway).
|
||||
</Step>
|
||||
<Step title="Skills (recommended)">
|
||||
- Reads the available skills and checks requirements.
|
||||
- Lets you choose a node manager: **npm / pnpm** (bun not recommended).
|
||||
- Installs optional dependencies (some use Homebrew on macOS).
|
||||
</Step>
|
||||
<Step title="Finish">
|
||||
- Summary + next steps, including iOS/Android/macOS apps for extra features.
|
||||
</Step>
|
||||
</Steps>
|
||||
|
||||
<Note>
|
||||
If no GUI is detected, the wizard prints SSH port-forward instructions for the Control UI instead of opening a browser.
|
||||
If the Control UI assets are missing, the wizard attempts to build them; fallback is `pnpm ui:build` (auto-installs UI deps).
|
||||
</Note>
|
||||
|
||||
## Non-interactive mode
|
||||
|
||||
Use `--non-interactive` to automate or script onboarding:
|
||||
|
||||
```bash
|
||||
openclaw onboard --non-interactive \
|
||||
--mode local \
|
||||
--auth-choice apiKey \
|
||||
--anthropic-api-key "$ANTHROPIC_API_KEY" \
|
||||
--gateway-port 18789 \
|
||||
--gateway-bind loopback \
|
||||
--install-daemon \
|
||||
--daemon-runtime node \
|
||||
--skip-skills
|
||||
```
|
||||
|
||||
Add `--json` for a machine‑readable summary.
|
||||
|
||||
<Note>
|
||||
`--json` does **not** imply non-interactive mode. Use `--non-interactive` (and `--workspace`) for scripts.
|
||||
</Note>
|
||||
|
||||
<AccordionGroup>
|
||||
<Accordion title="Gemini example">
|
||||
```bash
|
||||
openclaw onboard --non-interactive \
|
||||
--mode local \
|
||||
--auth-choice gemini-api-key \
|
||||
--gemini-api-key "$GEMINI_API_KEY" \
|
||||
--gateway-port 18789 \
|
||||
--gateway-bind loopback
|
||||
```
|
||||
</Accordion>
|
||||
<Accordion title="Z.AI example">
|
||||
```bash
|
||||
openclaw onboard --non-interactive \
|
||||
--mode local \
|
||||
--auth-choice zai-api-key \
|
||||
--zai-api-key "$ZAI_API_KEY" \
|
||||
--gateway-port 18789 \
|
||||
--gateway-bind loopback
|
||||
```
|
||||
</Accordion>
|
||||
<Accordion title="Vercel AI Gateway example">
|
||||
```bash
|
||||
openclaw onboard --non-interactive \
|
||||
--mode local \
|
||||
--auth-choice ai-gateway-api-key \
|
||||
--ai-gateway-api-key "$AI_GATEWAY_API_KEY" \
|
||||
--gateway-port 18789 \
|
||||
--gateway-bind loopback
|
||||
```
|
||||
</Accordion>
|
||||
<Accordion title="Cloudflare AI Gateway example">
|
||||
```bash
|
||||
openclaw onboard --non-interactive \
|
||||
--mode local \
|
||||
--auth-choice cloudflare-ai-gateway-api-key \
|
||||
--cloudflare-ai-gateway-account-id "your-account-id" \
|
||||
--cloudflare-ai-gateway-gateway-id "your-gateway-id" \
|
||||
--cloudflare-ai-gateway-api-key "$CLOUDFLARE_AI_GATEWAY_API_KEY" \
|
||||
--gateway-port 18789 \
|
||||
--gateway-bind loopback
|
||||
```
|
||||
</Accordion>
|
||||
<Accordion title="Moonshot example">
|
||||
```bash
|
||||
openclaw onboard --non-interactive \
|
||||
--mode local \
|
||||
--auth-choice moonshot-api-key \
|
||||
--moonshot-api-key "$MOONSHOT_API_KEY" \
|
||||
--gateway-port 18789 \
|
||||
--gateway-bind loopback
|
||||
```
|
||||
</Accordion>
|
||||
<Accordion title="Synthetic example">
|
||||
```bash
|
||||
openclaw onboard --non-interactive \
|
||||
--mode local \
|
||||
--auth-choice synthetic-api-key \
|
||||
--synthetic-api-key "$SYNTHETIC_API_KEY" \
|
||||
--gateway-port 18789 \
|
||||
--gateway-bind loopback
|
||||
```
|
||||
</Accordion>
|
||||
<Accordion title="OpenCode Zen example">
|
||||
```bash
|
||||
openclaw onboard --non-interactive \
|
||||
--mode local \
|
||||
--auth-choice opencode-zen \
|
||||
--opencode-zen-api-key "$OPENCODE_API_KEY" \
|
||||
--gateway-port 18789 \
|
||||
--gateway-bind loopback
|
||||
```
|
||||
</Accordion>
|
||||
</AccordionGroup>
|
||||
|
||||
### Add agent (non-interactive)
|
||||
|
||||
```bash
|
||||
openclaw agents add work \
|
||||
--workspace ~/.openclaw/workspace-work \
|
||||
--model openai/gpt-5.2 \
|
||||
--bind whatsapp:biz \
|
||||
--non-interactive \
|
||||
--json
|
||||
```
|
||||
|
||||
## Gateway wizard RPC
|
||||
|
||||
The Gateway exposes the wizard flow over RPC (`wizard.start`, `wizard.next`, `wizard.cancel`, `wizard.status`).
|
||||
Clients (macOS app, Control UI) can render steps without re‑implementing onboarding logic.
|
||||
|
||||
## Signal setup (signal-cli)
|
||||
|
||||
The wizard can install `signal-cli` from GitHub releases:
|
||||
|
||||
- Downloads the appropriate release asset.
|
||||
- Stores it under `~/.openclaw/tools/signal-cli/<version>/`.
|
||||
- Writes `channels.signal.cliPath` to your config.
|
||||
|
||||
Notes:
|
||||
|
||||
- JVM builds require **Java 21**.
|
||||
- Native builds are used when available.
|
||||
- Windows uses WSL2; signal-cli install follows the Linux flow inside WSL.
|
||||
|
||||
## What the wizard writes
|
||||
|
||||
Typical fields in `~/.openclaw/openclaw.json`:
|
||||
|
||||
- `agents.defaults.workspace`
|
||||
- `agents.defaults.model` / `models.providers` (if Minimax chosen)
|
||||
- `gateway.*` (mode, bind, auth, tailscale)
|
||||
- `channels.telegram.botToken`, `channels.discord.token`, `channels.signal.*`, `channels.imessage.*`
|
||||
- Channel allowlists (Slack/Discord/Matrix/Microsoft Teams) when you opt in during the prompts (names resolve to IDs when possible).
|
||||
- `skills.install.nodeManager`
|
||||
- `wizard.lastRunAt`
|
||||
- `wizard.lastRunVersion`
|
||||
- `wizard.lastRunCommit`
|
||||
- `wizard.lastRunCommand`
|
||||
- `wizard.lastRunMode`
|
||||
|
||||
`openclaw agents add` writes `agents.list[]` and optional `bindings`.
|
||||
|
||||
WhatsApp credentials go under `~/.openclaw/credentials/whatsapp/<accountId>/`.
|
||||
Sessions are stored under `~/.openclaw/agents/<agentId>/sessions/`.
|
||||
|
||||
Some channels are delivered as plugins. When you pick one during onboarding, the wizard
|
||||
will prompt to install it (npm or a local path) before it can be configured.
|
||||
|
||||
## Related docs
|
||||
|
||||
- Wizard overview: [Onboarding Wizard](/start/wizard)
|
||||
- macOS app onboarding: [Onboarding](/start/onboarding)
|
||||
- Config reference: [Gateway configuration](/gateway/configuration)
|
||||
- Providers: [WhatsApp](/channels/whatsapp), [Telegram](/channels/telegram), [Discord](/channels/discord), [Google Chat](/channels/googlechat), [Signal](/channels/signal), [BlueBubbles](/channels/bluebubbles) (iMessage), [iMessage](/channels/imessage) (legacy)
|
||||
- Skills: [Skills](/tools/skills), [Skills config](/tools/skills-config)
|
||||
41
docs/start/bootstrapping.md
Normal file
41
docs/start/bootstrapping.md
Normal file
@@ -0,0 +1,41 @@
|
||||
---
|
||||
summary: "Agent bootstrapping ritual that seeds the workspace and identity files"
|
||||
read_when:
|
||||
- Understanding what happens on the first agent run
|
||||
- Explaining where bootstrapping files live
|
||||
- Debugging onboarding identity setup
|
||||
title: "Agent Bootstrapping"
|
||||
sidebarTitle: "Bootstrapping"
|
||||
---
|
||||
|
||||
# Agent Bootstrapping
|
||||
|
||||
Bootstrapping is the **first‑run** ritual that prepares an agent workspace and
|
||||
collects identity details. It happens after onboarding, when the agent starts
|
||||
for the first time.
|
||||
|
||||
## What bootstrapping does
|
||||
|
||||
On the first agent run, OpenClaw bootstraps the workspace (default
|
||||
`~/.openclaw/workspace`):
|
||||
|
||||
- Seeds `AGENTS.md`, `BOOTSTRAP.md`, `IDENTITY.md`, `USER.md`.
|
||||
- Runs a short Q&A ritual (one question at a time).
|
||||
- Writes identity + preferences to `IDENTITY.md`, `USER.md`, `SOUL.md`.
|
||||
- Removes `BOOTSTRAP.md` when finished so it only runs once.
|
||||
|
||||
## Where it runs
|
||||
|
||||
Bootstrapping always runs on the **gateway host**. If the macOS app connects to
|
||||
a remote Gateway, the workspace and bootstrapping files live on that remote
|
||||
machine.
|
||||
|
||||
<Note>
|
||||
When the Gateway runs on another machine, edit workspace files on the gateway
|
||||
host (for example, `user@gateway-host:~/.openclaw/workspace`).
|
||||
</Note>
|
||||
|
||||
## Related docs
|
||||
|
||||
- macOS app onboarding: [Onboarding](/start/onboarding)
|
||||
- Workspace layout: [Agent workspace](/concepts/agent-workspace)
|
||||
64
docs/start/docs-directory.md
Normal file
64
docs/start/docs-directory.md
Normal file
@@ -0,0 +1,64 @@
|
||||
---
|
||||
summary: "Curated links to the most used OpenClaw docs."
|
||||
read_when:
|
||||
- You want quick access to key docs pages
|
||||
title: "Docs directory"
|
||||
---
|
||||
|
||||
<Note>
|
||||
This page is a curated index. If you are new, start with [Getting Started](/start/getting-started).
|
||||
For a complete map of the docs, see [Docs hubs](/start/hubs).
|
||||
</Note>
|
||||
|
||||
## Start here
|
||||
|
||||
- [Docs hubs (all pages linked)](/start/hubs)
|
||||
- [Help](/help)
|
||||
- [Configuration](/gateway/configuration)
|
||||
- [Configuration examples](/gateway/configuration-examples)
|
||||
- [Slash commands](/tools/slash-commands)
|
||||
- [Multi-agent routing](/concepts/multi-agent)
|
||||
- [Updating and rollback](/install/updating)
|
||||
- [Pairing (DM and nodes)](/start/pairing)
|
||||
- [Nix mode](/install/nix)
|
||||
- [OpenClaw assistant setup](/start/openclaw)
|
||||
- [Skills](/tools/skills)
|
||||
- [Skills config](/tools/skills-config)
|
||||
- [Workspace templates](/reference/templates/AGENTS)
|
||||
- [RPC adapters](/reference/rpc)
|
||||
- [Gateway runbook](/gateway)
|
||||
- [Nodes (iOS and Android)](/nodes)
|
||||
- [Web surfaces (Control UI)](/web)
|
||||
- [Discovery and transports](/gateway/discovery)
|
||||
- [Remote access](/gateway/remote)
|
||||
|
||||
## Providers and UX
|
||||
|
||||
- [WebChat](/web/webchat)
|
||||
- [Control UI (browser)](/web/control-ui)
|
||||
- [Telegram](/channels/telegram)
|
||||
- [Discord](/channels/discord)
|
||||
- [Mattermost (plugin)](/channels/mattermost)
|
||||
- [BlueBubbles (iMessage)](/channels/bluebubbles)
|
||||
- [iMessage (legacy)](/channels/imessage)
|
||||
- [Groups](/concepts/groups)
|
||||
- [WhatsApp group messages](/concepts/group-messages)
|
||||
- [Media images](/nodes/images)
|
||||
- [Media audio](/nodes/audio)
|
||||
|
||||
## Companion apps
|
||||
|
||||
- [macOS app](/platforms/macos)
|
||||
- [iOS app](/platforms/ios)
|
||||
- [Android app](/platforms/android)
|
||||
- [Windows (WSL2)](/platforms/windows)
|
||||
- [Linux app](/platforms/linux)
|
||||
|
||||
## Operations and safety
|
||||
|
||||
- [Sessions](/concepts/session)
|
||||
- [Cron jobs](/automation/cron-jobs)
|
||||
- [Webhooks](/automation/webhook)
|
||||
- [Gmail hooks (Pub/Sub)](/automation/gmail-pubsub)
|
||||
- [Security](/gateway/security)
|
||||
- [Troubleshooting](/gateway/troubleshooting)
|
||||
@@ -1,208 +1,120 @@
|
||||
---
|
||||
summary: "Beginner guide: from zero to first message (wizard, auth, channels, pairing)"
|
||||
summary: "Get OpenClaw installed and run your first chat in minutes."
|
||||
read_when:
|
||||
- First time setup from zero
|
||||
- You want the fastest path from install → onboarding → first message
|
||||
- You want the fastest path to a working chat
|
||||
title: "Getting Started"
|
||||
---
|
||||
|
||||
# Getting Started
|
||||
|
||||
Goal: go from **zero** → **first working chat** (with sane defaults) as quickly as possible.
|
||||
Goal: go from zero to a first working chat with minimal setup.
|
||||
|
||||
<Info>
|
||||
Fastest chat: open the Control UI (no channel setup needed). Run `openclaw dashboard`
|
||||
and chat in the browser, or open `http://127.0.0.1:18789/` on the gateway host.
|
||||
and chat in the browser, or open `http://127.0.0.1:18789/` on the
|
||||
<Tooltip headline="Gateway host" tip="The machine running the OpenClaw gateway service.">gateway host</Tooltip>.
|
||||
Docs: [Dashboard](/web/dashboard) and [Control UI](/web/control-ui).
|
||||
</Info>
|
||||
|
||||
Recommended path: use the **CLI onboarding wizard** (`openclaw onboard`). It sets up:
|
||||
## Prereqs
|
||||
|
||||
- model/auth (OAuth recommended)
|
||||
- gateway settings
|
||||
- channels (WhatsApp/Telegram/Discord/Mattermost (plugin)/...)
|
||||
- pairing defaults (secure DMs)
|
||||
- workspace bootstrap + skills
|
||||
- optional background service
|
||||
- Node 22 or newer
|
||||
|
||||
If you want the deeper reference pages, jump to: [Wizard](/start/wizard), [Setup](/start/setup), [Pairing](/start/pairing), [Security](/gateway/security).
|
||||
<Tip>
|
||||
Check your Node version with `node --version` if you are unsure.
|
||||
</Tip>
|
||||
|
||||
Sandboxing note: `agents.defaults.sandbox.mode: "non-main"` uses `session.mainKey` (default `"main"`),
|
||||
so group/channel sessions are sandboxed. If you want the main agent to always
|
||||
run on host, set an explicit per-agent override:
|
||||
## Quick setup (CLI)
|
||||
|
||||
```json
|
||||
{
|
||||
"routing": {
|
||||
"agents": {
|
||||
"main": {
|
||||
"workspace": "~/.openclaw/workspace",
|
||||
"sandbox": { "mode": "off" }
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
```
|
||||
<Steps>
|
||||
<Step title="Install OpenClaw (recommended)">
|
||||
<Tabs>
|
||||
<Tab title="macOS/Linux">
|
||||
```bash
|
||||
curl -fsSL https://openclaw.ai/install.sh | bash
|
||||
```
|
||||
</Tab>
|
||||
<Tab title="Windows (PowerShell)">
|
||||
```powershell
|
||||
iwr -useb https://openclaw.ai/install.ps1 | iex
|
||||
```
|
||||
</Tab>
|
||||
</Tabs>
|
||||
|
||||
## 0) Prereqs
|
||||
<Note>
|
||||
Other install methods and requirements: [Install](/install).
|
||||
</Note>
|
||||
|
||||
- Node `>=22`
|
||||
- `pnpm` (optional; recommended if you build from source)
|
||||
- **Recommended:** Brave Search API key for web search. Easiest path:
|
||||
`openclaw configure --section web` (stores `tools.web.search.apiKey`).
|
||||
See [Web tools](/tools/web).
|
||||
</Step>
|
||||
<Step title="Run the onboarding wizard">
|
||||
```bash
|
||||
openclaw onboard --install-daemon
|
||||
```
|
||||
|
||||
macOS: if you plan to build the apps, install Xcode / CLT. For the CLI + gateway only, Node is enough.
|
||||
Windows: use **WSL2** (Ubuntu recommended). WSL2 is strongly recommended; native Windows is untested, more problematic, and has poorer tool compatibility. Install WSL2 first, then run the Linux steps inside WSL. See [Windows (WSL2)](/platforms/windows).
|
||||
The wizard configures auth, gateway settings, and optional channels.
|
||||
See [Onboarding Wizard](/start/wizard) for details.
|
||||
|
||||
## 1) Install the CLI (recommended)
|
||||
</Step>
|
||||
<Step title="Check the Gateway">
|
||||
If you installed the service, it should already be running:
|
||||
|
||||
```bash
|
||||
curl -fsSL https://openclaw.ai/install.sh | bash
|
||||
```
|
||||
```bash
|
||||
openclaw gateway status
|
||||
```
|
||||
|
||||
Installer options (install method, non-interactive, from GitHub): [Install](/install).
|
||||
</Step>
|
||||
<Step title="Open the Control UI">
|
||||
```bash
|
||||
openclaw dashboard
|
||||
```
|
||||
</Step>
|
||||
</Steps>
|
||||
|
||||
Windows (PowerShell):
|
||||
<Check>
|
||||
If the Control UI loads, your Gateway is ready for use.
|
||||
</Check>
|
||||
|
||||
```powershell
|
||||
iwr -useb https://openclaw.ai/install.ps1 | iex
|
||||
```
|
||||
## Optional checks and extras
|
||||
|
||||
Alternative (global install):
|
||||
<AccordionGroup>
|
||||
<Accordion title="Run the Gateway in the foreground">
|
||||
Useful for quick tests or troubleshooting.
|
||||
|
||||
```bash
|
||||
npm install -g openclaw@latest
|
||||
```
|
||||
```bash
|
||||
openclaw gateway --port 18789
|
||||
```
|
||||
|
||||
```bash
|
||||
pnpm add -g openclaw@latest
|
||||
```
|
||||
</Accordion>
|
||||
<Accordion title="Send a test message">
|
||||
Requires a configured channel.
|
||||
|
||||
## 2) Run the onboarding wizard (and install the service)
|
||||
```bash
|
||||
openclaw message send --target +15555550123 --message "Hello from OpenClaw"
|
||||
```
|
||||
|
||||
```bash
|
||||
openclaw onboard --install-daemon
|
||||
```
|
||||
</Accordion>
|
||||
</AccordionGroup>
|
||||
|
||||
What you’ll choose:
|
||||
## Go deeper
|
||||
|
||||
- **Local vs Remote** gateway
|
||||
- **Auth**: OpenAI Code (Codex) subscription (OAuth) or API keys. For Anthropic we recommend an API key; `claude setup-token` is also supported.
|
||||
- **Providers**: WhatsApp QR login, Telegram/Discord bot tokens, Mattermost plugin tokens, etc.
|
||||
- **Daemon**: background install (launchd/systemd; WSL2 uses systemd)
|
||||
- **Runtime**: Node (recommended; required for WhatsApp/Telegram). Bun is **not recommended**.
|
||||
- **Gateway token**: the wizard generates one by default (even on loopback) and stores it in `gateway.auth.token`.
|
||||
<Columns>
|
||||
<Card title="Onboarding Wizard (details)" href="/start/wizard">
|
||||
Full CLI wizard reference and advanced options.
|
||||
</Card>
|
||||
<Card title="macOS app onboarding" href="/start/onboarding">
|
||||
First run flow for the macOS app.
|
||||
</Card>
|
||||
</Columns>
|
||||
|
||||
Wizard doc: [Wizard](/start/wizard)
|
||||
## What you will have
|
||||
|
||||
### Auth: where it lives (important)
|
||||
- A running Gateway
|
||||
- Auth configured
|
||||
- Control UI access or a connected channel
|
||||
|
||||
- **Recommended Anthropic path:** set an API key (wizard can store it for service use). `claude setup-token` is also supported if you want to reuse Claude Code credentials.
|
||||
## Next steps
|
||||
|
||||
- OAuth credentials (legacy import): `~/.openclaw/credentials/oauth.json`
|
||||
- Auth profiles (OAuth + API keys): `~/.openclaw/agents/<agentId>/agent/auth-profiles.json`
|
||||
|
||||
Headless/server tip: do OAuth on a normal machine first, then copy `oauth.json` to the gateway host.
|
||||
|
||||
## 3) Start the Gateway
|
||||
|
||||
If you installed the service during onboarding, the Gateway should already be running:
|
||||
|
||||
```bash
|
||||
openclaw gateway status
|
||||
```
|
||||
|
||||
Manual run (foreground):
|
||||
|
||||
```bash
|
||||
openclaw gateway --port 18789 --verbose
|
||||
```
|
||||
|
||||
Dashboard (local loopback): `http://127.0.0.1:18789/`
|
||||
If a token is configured, paste it into the Control UI settings (stored as `connect.params.auth.token`).
|
||||
|
||||
⚠️ **Bun warning (WhatsApp + Telegram):** Bun has known issues with these
|
||||
channels. If you use WhatsApp or Telegram, run the Gateway with **Node**.
|
||||
|
||||
## 3.5) Quick verify (2 min)
|
||||
|
||||
```bash
|
||||
openclaw status
|
||||
openclaw health
|
||||
openclaw security audit --deep
|
||||
```
|
||||
|
||||
## 4) Pair + connect your first chat surface
|
||||
|
||||
### WhatsApp (QR login)
|
||||
|
||||
```bash
|
||||
openclaw channels login
|
||||
```
|
||||
|
||||
Scan via WhatsApp → Settings → Linked Devices.
|
||||
|
||||
WhatsApp doc: [WhatsApp](/channels/whatsapp)
|
||||
|
||||
### Telegram / Discord / others
|
||||
|
||||
The wizard can write tokens/config for you. If you prefer manual config, start with:
|
||||
|
||||
- Telegram: [Telegram](/channels/telegram)
|
||||
- Discord: [Discord](/channels/discord)
|
||||
- Mattermost (plugin): [Mattermost](/channels/mattermost)
|
||||
|
||||
**Telegram DM tip:** your first DM returns a pairing code. Approve it (see next step) or the bot won’t respond.
|
||||
|
||||
## 5) DM safety (pairing approvals)
|
||||
|
||||
Default posture: unknown DMs get a short code and messages are not processed until approved.
|
||||
If your first DM gets no reply, approve the pairing:
|
||||
|
||||
```bash
|
||||
openclaw pairing list whatsapp
|
||||
openclaw pairing approve whatsapp <code>
|
||||
```
|
||||
|
||||
Pairing doc: [Pairing](/start/pairing)
|
||||
|
||||
## From source (development)
|
||||
|
||||
If you’re hacking on OpenClaw itself, run from source:
|
||||
|
||||
```bash
|
||||
git clone https://github.com/openclaw/openclaw.git
|
||||
cd openclaw
|
||||
pnpm install
|
||||
pnpm ui:build # auto-installs UI deps on first run
|
||||
pnpm build
|
||||
openclaw onboard --install-daemon
|
||||
```
|
||||
|
||||
If you don’t have a global install yet, run the onboarding step via `pnpm openclaw ...` from the repo.
|
||||
`pnpm build` also bundles A2UI assets; if you need to run just that step, use `pnpm canvas:a2ui:bundle`.
|
||||
|
||||
Gateway (from this repo):
|
||||
|
||||
```bash
|
||||
node openclaw.mjs gateway --port 18789 --verbose
|
||||
```
|
||||
|
||||
## 7) Verify end-to-end
|
||||
|
||||
In a new terminal, send a test message:
|
||||
|
||||
```bash
|
||||
openclaw message send --target +15555550123 --message "Hello from OpenClaw"
|
||||
```
|
||||
|
||||
If `openclaw health` shows “no auth configured”, go back to the wizard and set OAuth/key auth — the agent won’t be able to respond without it.
|
||||
|
||||
Tip: `openclaw status --all` is the best pasteable, read-only debug report.
|
||||
Health probes: `openclaw health` (or `openclaw status --deep`) asks the running gateway for a health snapshot.
|
||||
|
||||
## Next steps (optional, but great)
|
||||
|
||||
- macOS menu bar app + voice wake: [macOS app](/platforms/macos)
|
||||
- iOS/Android nodes (Canvas/camera/voice): [Nodes](/nodes)
|
||||
- Remote access (SSH tunnel / Tailscale Serve): [Remote access](/gateway/remote) and [Tailscale](/gateway/tailscale)
|
||||
- Always-on / VPN setups: [Remote access](/gateway/remote), [exe.dev](/platforms/exe-dev), [Hetzner](/platforms/hetzner), [macOS remote](/platforms/mac/remote)
|
||||
- DM safety and approvals: [Pairing](/start/pairing)
|
||||
- Connect more channels: [Channels](/channels)
|
||||
- Advanced workflows and from source: [Setup](/start/setup)
|
||||
|
||||
@@ -7,17 +7,23 @@ title: "Docs Hubs"
|
||||
|
||||
# Docs hubs
|
||||
|
||||
<Note>
|
||||
If you are new to OpenClaw, start with [Getting Started](/start/getting-started).
|
||||
</Note>
|
||||
|
||||
Use these hubs to discover every page, including deep dives and reference docs that don’t appear in the left nav.
|
||||
|
||||
## Start here
|
||||
|
||||
- [Index](/)
|
||||
- [Getting Started](/start/getting-started)
|
||||
- [Quick start](/start/quickstart)
|
||||
- [Onboarding](/start/onboarding)
|
||||
- [Wizard](/start/wizard)
|
||||
- [Setup](/start/setup)
|
||||
- [Dashboard (local Gateway)](http://127.0.0.1:18789/)
|
||||
- [Help](/help)
|
||||
- [Docs directory](/start/docs-directory)
|
||||
- [Configuration](/gateway/configuration)
|
||||
- [Configuration examples](/gateway/configuration-examples)
|
||||
- [OpenClaw assistant](/start/openclaw)
|
||||
@@ -34,6 +40,7 @@ Use these hubs to discover every page, including deep dives and reference docs t
|
||||
## Core concepts
|
||||
|
||||
- [Architecture](/concepts/architecture)
|
||||
- [Features](/concepts/features)
|
||||
- [Network hub](/network)
|
||||
- [Agent runtime](/concepts/agent)
|
||||
- [Agent workspace](/concepts/agent-workspace)
|
||||
@@ -81,6 +88,7 @@ Use these hubs to discover every page, including deep dives and reference docs t
|
||||
## Gateway + operations
|
||||
|
||||
- [Gateway runbook](/gateway)
|
||||
- [Network model](/gateway/network-model)
|
||||
- [Gateway pairing](/gateway/pairing)
|
||||
- [Gateway lock](/gateway/gateway-lock)
|
||||
- [Background process](/gateway/background-process)
|
||||
@@ -178,6 +186,10 @@ Use these hubs to discover every page, including deep dives and reference docs t
|
||||
- [Research: memory](/experiments/research/memory)
|
||||
- [Model config exploration](/experiments/proposals/model-config)
|
||||
|
||||
## Project
|
||||
|
||||
- [Credits](/reference/credits)
|
||||
|
||||
## Testing + release
|
||||
|
||||
- [Testing](/reference/test)
|
||||
|
||||
@@ -3,108 +3,78 @@ summary: "First-run onboarding flow for OpenClaw (macOS app)"
|
||||
read_when:
|
||||
- Designing the macOS onboarding assistant
|
||||
- Implementing auth or identity setup
|
||||
title: "Onboarding"
|
||||
title: "Onboarding (macOS App)"
|
||||
sidebarTitle: "Onboarding: macOS App"
|
||||
---
|
||||
|
||||
# Onboarding (macOS app)
|
||||
# Onboarding (macOS App)
|
||||
|
||||
This doc describes the **current** first‑run onboarding flow. The goal is a
|
||||
smooth “day 0” experience: pick where the Gateway runs, connect auth, run the
|
||||
wizard, and let the agent bootstrap itself.
|
||||
|
||||
## Page order (current)
|
||||
|
||||
1. Welcome + security notice
|
||||
2. **Gateway selection** (Local / Remote / Configure later)
|
||||
3. **Auth (Anthropic OAuth)** — local only
|
||||
4. **Setup Wizard** (Gateway‑driven)
|
||||
5. **Permissions** (TCC prompts)
|
||||
6. **CLI** (optional)
|
||||
7. **Onboarding chat** (dedicated session)
|
||||
8. Ready
|
||||
|
||||
## 1) Welcome + security notice
|
||||
|
||||
Read the security notice displayed and decide accordingly.
|
||||
|
||||
## 2) Local vs Remote
|
||||
<Steps>
|
||||
<Step title="Approve macOS warning">
|
||||
<Frame>
|
||||
<img src="/assets/macos-onboarding/01-macos-warning.jpeg" alt="" />
|
||||
</Frame>
|
||||
</Step>
|
||||
<Step title="Approve find local networks">
|
||||
<Frame>
|
||||
<img src="/assets/macos-onboarding/02-local-networks.jpeg" alt="" />
|
||||
</Frame>
|
||||
</Step>
|
||||
<Step title="Welcome and security notice">
|
||||
<Frame caption="Read the security notice displayed and decide accordingly">
|
||||
<img src="/assets/macos-onboarding/03-security-notice.png" alt="" />
|
||||
</Frame>
|
||||
</Step>
|
||||
<Step title="Local vs Remote">
|
||||
<Frame>
|
||||
<img src="/assets/macos-onboarding/04-choose-gateway.png" alt="" />
|
||||
</Frame>
|
||||
|
||||
Where does the **Gateway** run?
|
||||
|
||||
- **Local (this Mac):** onboarding can run OAuth flows and write credentials
|
||||
- **This Mac (Local only):** onboarding can run OAuth flows and write credentials
|
||||
locally.
|
||||
- **Remote (over SSH/Tailnet):** onboarding does **not** run OAuth locally;
|
||||
credentials must exist on the gateway host.
|
||||
- **Configure later:** skip setup and leave the app unconfigured.
|
||||
|
||||
Gateway auth tip:
|
||||
|
||||
<Tip>
|
||||
**Gateway auth tip:**
|
||||
- The wizard now generates a **token** even for loopback, so local WS clients must authenticate.
|
||||
- If you disable auth, any local process can connect; use that only on fully trusted machines.
|
||||
- Use a **token** for multi‑machine access or non‑loopback binds.
|
||||
|
||||
## 3) Local-only auth (Anthropic OAuth)
|
||||
|
||||
The macOS app supports Anthropic OAuth (Claude Pro/Max). The flow:
|
||||
|
||||
- Opens the browser for OAuth (PKCE)
|
||||
- Asks the user to paste the `code#state` value
|
||||
- Writes credentials to `~/.openclaw/credentials/oauth.json`
|
||||
|
||||
Other providers (OpenAI, custom APIs) are configured via environment variables
|
||||
or config files for now.
|
||||
|
||||
## 4) Setup Wizard (Gateway‑driven)
|
||||
|
||||
The app can run the same setup wizard as the CLI. This keeps onboarding in sync
|
||||
with Gateway‑side behavior and avoids duplicating logic in SwiftUI.
|
||||
|
||||
## 5) Permissions
|
||||
</Tip>
|
||||
</Step>
|
||||
<Step title="Permissions">
|
||||
<Frame caption="Choose what permissions do you want to give OpenClaw">
|
||||
<img src="/assets/macos-onboarding/05-permissions.png" alt="" />
|
||||
</Frame>
|
||||
|
||||
Onboarding requests TCC permissions needed for:
|
||||
|
||||
- Automation (AppleScript)
|
||||
- Notifications
|
||||
- Accessibility
|
||||
- Screen Recording
|
||||
- Microphone / Speech Recognition
|
||||
- Automation (AppleScript)
|
||||
- Microphone
|
||||
- Speech Recognition
|
||||
- Camera
|
||||
- Location
|
||||
|
||||
## 6) CLI (optional)
|
||||
|
||||
The app can install the global `openclaw` CLI via npm/pnpm so terminal
|
||||
workflows and launchd tasks work out of the box.
|
||||
|
||||
## 7) Onboarding chat (dedicated session)
|
||||
|
||||
After setup, the app opens a dedicated onboarding chat session so the agent can
|
||||
introduce itself and guide next steps. This keeps first‑run guidance separate
|
||||
from your normal conversation.
|
||||
|
||||
## Agent bootstrap ritual
|
||||
|
||||
On the first agent run, OpenClaw bootstraps a workspace (default `~/.openclaw/workspace`):
|
||||
|
||||
- Seeds `AGENTS.md`, `BOOTSTRAP.md`, `IDENTITY.md`, `USER.md`
|
||||
- Runs a short Q&A ritual (one question at a time)
|
||||
- Writes identity + preferences to `IDENTITY.md`, `USER.md`, `SOUL.md`
|
||||
- Removes `BOOTSTRAP.md` when finished so it only runs once
|
||||
|
||||
## Optional: Gmail hooks (manual)
|
||||
|
||||
Gmail Pub/Sub setup is currently a manual step. Use:
|
||||
|
||||
```bash
|
||||
openclaw webhooks gmail setup --account you@gmail.com
|
||||
```
|
||||
|
||||
See [/automation/gmail-pubsub](/automation/gmail-pubsub) for details.
|
||||
|
||||
## Remote mode notes
|
||||
|
||||
When the Gateway runs on another machine, credentials and workspace files live
|
||||
**on that host**. If you need OAuth in remote mode, create:
|
||||
|
||||
- `~/.openclaw/credentials/oauth.json`
|
||||
- `~/.openclaw/agents/<agentId>/agent/auth-profiles.json`
|
||||
|
||||
on the gateway host.
|
||||
</Step>
|
||||
<Step title="CLI">
|
||||
<Info>This step is optional</Info>
|
||||
The app can install the global `openclaw` CLI via npm/pnpm so terminal
|
||||
workflows and launchd tasks work out of the box.
|
||||
</Step>
|
||||
<Step title="Onboarding Chat (dedicated session)">
|
||||
After setup, the app opens a dedicated onboarding chat session so the agent can
|
||||
introduce itself and guide next steps. This keeps first‑run guidance separate
|
||||
from your normal conversation. See [Bootstrapping](/start/bootstrapping) for
|
||||
what happens on the gateway host during the first agent run.
|
||||
</Step>
|
||||
</Steps>
|
||||
|
||||
@@ -26,26 +26,9 @@ Start conservative:
|
||||
|
||||
## Prerequisites
|
||||
|
||||
- Node **22+**
|
||||
- OpenClaw available on PATH (recommended: global install)
|
||||
- OpenClaw installed and onboarded — see [Getting Started](/start/getting-started) if you haven't done this yet
|
||||
- A second phone number (SIM/eSIM/prepaid) for the assistant
|
||||
|
||||
```bash
|
||||
npm install -g openclaw@latest
|
||||
# or: pnpm add -g openclaw@latest
|
||||
```
|
||||
|
||||
From source (development):
|
||||
|
||||
```bash
|
||||
git clone https://github.com/openclaw/openclaw.git
|
||||
cd openclaw
|
||||
pnpm install
|
||||
pnpm ui:build # auto-installs UI deps on first run
|
||||
pnpm build
|
||||
pnpm link --global
|
||||
```
|
||||
|
||||
## The two-phone setup (recommended)
|
||||
|
||||
You want this:
|
||||
@@ -142,7 +125,7 @@ Example:
|
||||
{
|
||||
logging: { level: "info" },
|
||||
agent: {
|
||||
model: "anthropic/claude-opus-4-5",
|
||||
model: "anthropic/claude-opus-4-6",
|
||||
workspace: "~/.openclaw/workspace",
|
||||
thinkingDefault: "high",
|
||||
timeoutSeconds: 1800,
|
||||
|
||||
22
docs/start/quickstart.md
Normal file
22
docs/start/quickstart.md
Normal file
@@ -0,0 +1,22 @@
|
||||
---
|
||||
summary: "Quick start has moved to Getting Started."
|
||||
read_when:
|
||||
- You are looking for the fastest setup steps
|
||||
- You were sent here from an older link
|
||||
title: "Quick start"
|
||||
---
|
||||
|
||||
# Quick start
|
||||
|
||||
<Info>
|
||||
Quick start is now part of [Getting Started](/start/getting-started).
|
||||
</Info>
|
||||
|
||||
<Columns>
|
||||
<Card title="Getting Started" href="/start/getting-started">
|
||||
Install OpenClaw and run your first chat in minutes.
|
||||
</Card>
|
||||
<Card title="Onboarding Wizard" href="/start/wizard">
|
||||
Full CLI wizard reference and advanced options.
|
||||
</Card>
|
||||
</Columns>
|
||||
@@ -1,5 +1,5 @@
|
||||
---
|
||||
summary: "Setup guide: keep your OpenClaw setup tailored while staying up-to-date"
|
||||
summary: "Advanced setup and development workflows for OpenClaw"
|
||||
read_when:
|
||||
- Setting up a new machine
|
||||
- You want “latest + greatest” without breaking your personal setup
|
||||
@@ -8,6 +8,11 @@ title: "Setup"
|
||||
|
||||
# Setup
|
||||
|
||||
<Note>
|
||||
If you are setting up for the first time, start with [Getting Started](/start/getting-started).
|
||||
For wizard details, see [Onboarding Wizard](/start/wizard).
|
||||
</Note>
|
||||
|
||||
Last updated: 2026-01-01
|
||||
|
||||
## TL;DR
|
||||
@@ -43,6 +48,14 @@ openclaw setup
|
||||
|
||||
If you don’t have a global install yet, run it via `pnpm openclaw setup`.
|
||||
|
||||
## Run the Gateway from this repo
|
||||
|
||||
After `pnpm build`, you can run the packaged CLI directly:
|
||||
|
||||
```bash
|
||||
node openclaw.mjs gateway --port 18789 --verbose
|
||||
```
|
||||
|
||||
## Stable workflow (macOS app first)
|
||||
|
||||
1. Install + launch **OpenClaw.app** (menu bar).
|
||||
|
||||
141
docs/start/wizard-cli-automation.md
Normal file
141
docs/start/wizard-cli-automation.md
Normal file
@@ -0,0 +1,141 @@
|
||||
---
|
||||
summary: "Scripted onboarding and agent setup for the OpenClaw CLI"
|
||||
read_when:
|
||||
- You are automating onboarding in scripts or CI
|
||||
- You need non-interactive examples for specific providers
|
||||
title: "CLI Automation"
|
||||
sidebarTitle: "CLI automation"
|
||||
---
|
||||
|
||||
# CLI Automation
|
||||
|
||||
Use `--non-interactive` to automate `openclaw onboard`.
|
||||
|
||||
<Note>
|
||||
`--json` does not imply non-interactive mode. Use `--non-interactive` (and `--workspace`) for scripts.
|
||||
</Note>
|
||||
|
||||
## Baseline non-interactive example
|
||||
|
||||
```bash
|
||||
openclaw onboard --non-interactive \
|
||||
--mode local \
|
||||
--auth-choice apiKey \
|
||||
--anthropic-api-key "$ANTHROPIC_API_KEY" \
|
||||
--gateway-port 18789 \
|
||||
--gateway-bind loopback \
|
||||
--install-daemon \
|
||||
--daemon-runtime node \
|
||||
--skip-skills
|
||||
```
|
||||
|
||||
Add `--json` for a machine-readable summary.
|
||||
|
||||
## Provider-specific examples
|
||||
|
||||
<AccordionGroup>
|
||||
<Accordion title="Gemini example">
|
||||
```bash
|
||||
openclaw onboard --non-interactive \
|
||||
--mode local \
|
||||
--auth-choice gemini-api-key \
|
||||
--gemini-api-key "$GEMINI_API_KEY" \
|
||||
--gateway-port 18789 \
|
||||
--gateway-bind loopback
|
||||
```
|
||||
</Accordion>
|
||||
<Accordion title="Z.AI example">
|
||||
```bash
|
||||
openclaw onboard --non-interactive \
|
||||
--mode local \
|
||||
--auth-choice zai-api-key \
|
||||
--zai-api-key "$ZAI_API_KEY" \
|
||||
--gateway-port 18789 \
|
||||
--gateway-bind loopback
|
||||
```
|
||||
</Accordion>
|
||||
<Accordion title="Vercel AI Gateway example">
|
||||
```bash
|
||||
openclaw onboard --non-interactive \
|
||||
--mode local \
|
||||
--auth-choice ai-gateway-api-key \
|
||||
--ai-gateway-api-key "$AI_GATEWAY_API_KEY" \
|
||||
--gateway-port 18789 \
|
||||
--gateway-bind loopback
|
||||
```
|
||||
</Accordion>
|
||||
<Accordion title="Cloudflare AI Gateway example">
|
||||
```bash
|
||||
openclaw onboard --non-interactive \
|
||||
--mode local \
|
||||
--auth-choice cloudflare-ai-gateway-api-key \
|
||||
--cloudflare-ai-gateway-account-id "your-account-id" \
|
||||
--cloudflare-ai-gateway-gateway-id "your-gateway-id" \
|
||||
--cloudflare-ai-gateway-api-key "$CLOUDFLARE_AI_GATEWAY_API_KEY" \
|
||||
--gateway-port 18789 \
|
||||
--gateway-bind loopback
|
||||
```
|
||||
</Accordion>
|
||||
<Accordion title="Moonshot example">
|
||||
```bash
|
||||
openclaw onboard --non-interactive \
|
||||
--mode local \
|
||||
--auth-choice moonshot-api-key \
|
||||
--moonshot-api-key "$MOONSHOT_API_KEY" \
|
||||
--gateway-port 18789 \
|
||||
--gateway-bind loopback
|
||||
```
|
||||
</Accordion>
|
||||
<Accordion title="Synthetic example">
|
||||
```bash
|
||||
openclaw onboard --non-interactive \
|
||||
--mode local \
|
||||
--auth-choice synthetic-api-key \
|
||||
--synthetic-api-key "$SYNTHETIC_API_KEY" \
|
||||
--gateway-port 18789 \
|
||||
--gateway-bind loopback
|
||||
```
|
||||
</Accordion>
|
||||
<Accordion title="OpenCode Zen example">
|
||||
```bash
|
||||
openclaw onboard --non-interactive \
|
||||
--mode local \
|
||||
--auth-choice opencode-zen \
|
||||
--opencode-zen-api-key "$OPENCODE_API_KEY" \
|
||||
--gateway-port 18789 \
|
||||
--gateway-bind loopback
|
||||
```
|
||||
</Accordion>
|
||||
</AccordionGroup>
|
||||
|
||||
## Add another agent
|
||||
|
||||
Use `openclaw agents add <name>` to create a separate agent with its own workspace,
|
||||
sessions, and auth profiles. Running without `--workspace` launches the wizard.
|
||||
|
||||
```bash
|
||||
openclaw agents add work \
|
||||
--workspace ~/.openclaw/workspace-work \
|
||||
--model openai/gpt-5.2 \
|
||||
--bind whatsapp:biz \
|
||||
--non-interactive \
|
||||
--json
|
||||
```
|
||||
|
||||
What it sets:
|
||||
|
||||
- `agents.list[].name`
|
||||
- `agents.list[].workspace`
|
||||
- `agents.list[].agentDir`
|
||||
|
||||
Notes:
|
||||
|
||||
- Default workspaces follow `~/.openclaw/workspace-<agentId>`.
|
||||
- Add `bindings` to route inbound messages (the wizard can do this).
|
||||
- Non-interactive flags: `--model`, `--agent-dir`, `--bind`, `--non-interactive`.
|
||||
|
||||
## Related docs
|
||||
|
||||
- Onboarding hub: [Onboarding Wizard (CLI)](/start/wizard)
|
||||
- Full reference: [CLI Onboarding Reference](/start/wizard-cli-reference)
|
||||
- Command reference: [`openclaw onboard`](/cli/onboard)
|
||||
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user