OpenClaw를 설치하면서 해보고 싶었던 것 중 하나가 검색 결과를 정리해서 Notion에 자동으로 문서를 만들어주는 기능이었다.

지금 OpenClaw에게 full 권한을 주었기에, 적당히 요청하면 어떻게든 될 것 같았지만, 추후에 다른 기능들도 설치하기 위해서, 이번에 환경을 제대로 구축해 두려고 했다.

 

Skill이란?

 

Skills - OpenClaw

 

docs.openclaw.ai

공식 문서에서는 Skill을 OpenClaw 에이전트에게 특정 작업을 수행하는 방법을 알려주는 확장 기능으로 설명하고 있다.

 

하나의 Skill은 보통 하나의 디렉터리 형태로 구성되며, SKILL.md를 통해 OpenClaw에게 해당 기능을 어떻게 수행해야 하는지를 알려준다.

 

핵심 파일인 SKILL.md 에는 아래와 같은 정보가 들어있다.

  • 어떤 작업을 수행하는지
  • 어떤 도구를 사용해야 하는지
  • 어떤 방식으로 실행해야 하는지

개인적으로는, skills를 아래와 같이 비유할 수 있다고 생각한다.

OpenClaw를 모험가라고 생각하면, Skills는 그 모험가의 능력이다.

모험가
├─ 검 공격 (전사 스킬)
├─ 파이어볼 (마법 스킬)
├─ 탐색 (정찰 스킬)
└─ 제작 (크래프트 스킬)

 

즉 OpenClaw에게 Skills를 추가한다는 것은, 모험가가 새로운 기술을 배우는 것 과 비슷하다.

개발자스럽게 비유하자면 OpenClaw는 VSCode, Skills는 Extensions 같은 느낌이라고 볼 수 있다.

 

필요한 기능을 Skills 형태로 추가하면, OpenClaw가 그 기능을 수행할 수 있게 된다.

 

설치 시작

Skills를 설치하기 위해서는 ClawHub를 사용한다.

 

ClawHub - OpenClaw

 

docs.openclaw.ai

 

ClawHub는 OpenClaw에서 사용하는 공식 Skills 레지스트리로, 사용자들이 만든 Skills를 검색하고 설치할 수 있는 곳이다.

하지만 docker로 기동한 OpenClaw에는 clawhub가 설치되어 있지 않았다.

# OpenClaw 컨테이너 내부에서 실행
$ npx clawhub
Need to install the following packages: clawhub@0.8.0

 

 

이렇게 하면 설치할 수 있지만, npm과 node_modules가 volume으로 관리되고 있지 않기 때문에, 컨테이너가 재기동되면 clawhub가 사라지는 문제가 발생한다.

그래서 영구적으로 설치하기 위해, Dockerfile에서 설치하도록 추가한다.

vi Dockerfile

# 추가할 내용 (RUN pnpm build 이후)
USER root
RUN npm install -g clawhub
USER node

OpenClaw runtime 단계에서 CLI를 추가하는 게 좋을 것 같아서, pnpm build 이후에 설치하도록 추가했다.

 

파일을 저장한 후, 재시작을 해 준다.

# 종료
docker compose down

# 빌드 및 시작
sudo ./docker-setup.sh

# 빌드 후 나오는 설정창은 ESC를 눌러서 닫아주면 된다.

 

그럼 clawhub가 정상적으로 설치되었는지 확인해 보자.

docker compose run --rm openclaw-cli clawhub --version

 

오늘의 잡담

블로그엔 소개하지 않았지만, 매일 아침 7시에 날씨정보를 알려달라고 OpenClaw에게 요청했었다.

 

그랬었다 보니, 나도 모르는 사이에 Skill이 설치되어 있었다.

# 설치된 skills 확인 하는 명령어
docker compose run --rm openclaw-cli skills

 

full 권한을 줬다 보니, 스스로 뭔가를 잘 하기는 하는데, 역시 무섭긴 하다 (...)

가방을 구매하고 싶어서 찾던 도중, OpenClaw에게 시켜보고 싶다는 생각이 들어서, 요청을 했다.

그러나 기본 설정 상태의 OpenClaw는 웹 조회 권한이 없는 듯했다.

 

직접 찾기 귀찮으니, 오늘은 웹 조회 권한을 줘 보기로 했다.

방법 조사

가장 확실한 방법일 것 같아서 OpenClaw에게 직접 물어보았다.

 

검색 공급자를 설정해 달라고 하는 답변이 왔다.

선택하지 않고, 직접 브라우저를 기동 해서 확인할 수 있게 할 순 없을까 하는 생각에 다시 한번 질문을 했지만, 정말 단호한 답변이 돌아왔다.

 

내가 생각하던 것 과는 다르다는 느낌이 들어서 직접 알아보기로 했다 (...)

 

공식 문서를 알아보던 중, Browser에 관한 문서가 있었다. 여기에는 내가 원하던 방식인 Docker환경에서 Playwright를 설치하는 방법이 포함되어 있었다.

 

Browser (OpenClaw-managed) - OpenClaw

Browser (OpenClaw-managed)

docs.openclaw.ai

 

이 문서 정보를 OpenClaw에게 넣어서 확인을 하면 가능한지 답이 나올 것 같아서 한번 더 질문했다.

 

좋아. 가능성이 보이기 시작했다.

 

OpenClaw의 답변에 의하면, 성공 조건은 4가지이다.

1) OpenClaw 도구 프로필이 messaging이 아닌 로컬 실행 가능 프로필
2) 컨테이너에 Playwright 브라우저/의존성 설치 완료
3) 컨테이너 재기동 후 OpenClaw가 해당 도구를 인식
4) --shm-size(또는 ipc) 부족하지 않게 설정

설치 시작

1) OpenClaw 도구 프로필이 messaging이 아닌 로컬 실행 가능 프로필로 변경하기

 

Tools - OpenClaw

 

docs.openclaw.ai

이번에도 공식 문서와 함께 하기로 했다.

해당 설정은 openclaw.json파일에서 확인할 수 있다.

파일 경로에 대한 설명은 이전 글을 참고한다.

$ sudo cat /root/.openclaw/openclaw.json

{
  ...
  "tools": {
    "profile": "messaging"
  },
  ... 
}

 

파일을 확인해 보니, profile이 messaging으로 되어있다.

공식 문서에는 여러 가지 상세한 설정이 가능한 것으로 보였지만, 전부 읽어보기 귀찮았기에, OpenClaw에게 질문을 했다.

 

뭐..? 그게 가능해?

공식문서에는 local이라는 profile은 보이지 않았지만, 속는 셈 치고 해 보기로 했다.

역시나 그럴 리 없었다.

빠르게 포기하고, 수동으로 변경을 시도했다.

우선 나는 Docker 환경이고, Ubuntu Server 자체에 크게 중요한 내용은 없었기에, full 권한을 주기로 했다.

$ sudo vi /root/.openclaw/openclaw.json
# 아래처럼 변경
{
  ...
  "tools": {
    "profile": "full"
  },
  ... 
}

 

일단 이걸로 설정은 되었을 거라 믿고, 다음을 진행하기로 했다.

2) 컨테이너에 Playwright 브라우저/의존성 설치하기

공식 문서에는 이렇게 적혀있었다.

If your Gateway runs in Docker, avoid npx playwright (npm override conflicts). Use the bundled CLI instead

Gateway가 Docker에서 실행되는 경우 npx playwright(npm 오버라이드 충돌)를 사용하지 말 것. 대신 번들로 제공되는 CLI를 사용할 것

 

그리고 아래와 같은 명령어가 제시되어 있었다.

docker compose run --rm openclaw-cli \
  node /app/node_modules/playwright-core/cli.js install chromium

 

공식 문서의 명령어 아래에는 이런 문구가 적혀있다.

To persist browser downloads, set PLAYWRIGHT_BROWSERS_PATH (for example, /home/node/.cache/ms-playwright) and make sure /home/node is persisted via OPENCLAW_HOME_VOLUME or a bind mount. See Docker.

브라우저 다운로드를 지속하려면 PLAYWRIGHT_BROWSERS_PATH(예: /home/node/.cache/ms-playwright)를 설정하고, /home/node가 OPENCLAW_HOME_VOLUME 또는 바인드 마운트를 통해 지속되도록 하십시오. Docker를 참조하십시오.

 

Playwright가 내려받은 브라우저 바이너리를 재사용하기 위한 설정으로, 단순히 실행만 하면, 볼륨 영속화가 되지 않아서, 재시작할 때 사라지는 문제가 발생한다.

참조하라고 하는 Docker 링크로 가게 되면, 이런 내용을 확인할 수 있다.

Persist Playwright browser downloads:
・Set PLAYWRIGHT_BROWSERS_PATH=/home/node/.cache/ms-playwright in docker-compose.yml.
・Ensure /home/node persists via OPENCLAW_HOME_VOLUME, or mount /home/node/.cache/ms-playwright via OPENCLAW_EXTRA_MOUNTS.

Persist Playwright 브라우저 다운로드:
・docker-compose.yml에서 PLAYWRIGHT_BROWSERS_PATH=/home/node/.cache/ms-playwright 설정.
・OPENCLAW_HOME_VOLUME을 통해 /home/node가 유지되도록 하거나, OPENCLAW_EXTRA_MOUNTS를 통해 /home/node/.cache/ms-playwright를 마운트 하십시오.

 

그럼 먼저, docker-compose.yml 파일을 수정하도록 하자.

sudo vi docker-compose.yml

# 아래와 같이 수정
services:
  openclaw-gateway:
    image: ${OPENCLAW_IMAGE:-openclaw:local}
    environment:
      ...
      PLAYWRIGHT_BROWSERS_PATH: /home/node/.cache/ms-playwright # 이 줄을 추가
      ...
    volumes:
      ...
      - ${PLAYWRIGHT_CACHE_DIR}:/home/node/.cache/ms-playwright # 이 줄을 추가
    ...
  openclaw-cli:
    environment:
      ...
      PLAYWRIGHT_BROWSERS_PATH: /home/node/.cache/ms-playwright # 이 줄을 추가
    volumes:
      ...
      - ${PLAYWRIGHT_CACHE_DIR}:/home/node/.cache/ms-playwright # 이 줄을 추가
...

 

그리고 .env파일을 수정한다.

sudo vi .env

...
# 마지막 줄에 추가
PLAYWRIGHT_CACHE_DIR=/root/.openclaw/ms-playwright

 

그 후, 호스트 디렉터리를 작성해 준다.

sudo mkdir -p /root/.openclaw/ms-playwright

# 권한 설정
# 참고자료 : https://docs.openclaw.ai/install/docker#permissions-+-eacces
sudo chown -R 1000:1000 /root/.openclaw

 

이 수정으로, 공식문서와는 조금 다르지만, volume으로 연결하여, playwright관련 파일들을 컨테이너 삭제 후에도 유지되도록 할 수 있다.

 

이후, docker compose down, up으로 완전한 재기동을 해 주고, chromium을 설치하는 명령어를 수행한다.

# docker 재기동
docker compose down
docker compose up -d

# 설치 명령어 수행
docker compose run --rm openclaw-cli \
  node /app/node_modules/playwright-core/cli.js install chromium

 

명령어를 실행했지만, 에러가 발생했다.

 

기본 entrypoint가 OpenClaw CLI로 되어있기 때문에 해당 문제가 발생하는 것 같다.

아래의 명령어로 바꾸어 실행해 본다.

docker compose run --rm --entrypoint node openclaw-cli \
  /app/node_modules/playwright-core/cli.js install chromium

문제없이 설치되는 것 같다.

 

컨테이너에 직접 들어가서 설치하는 방법 또한 가능하다. (참고용)

더보기

파일이 존재하는지 확인부터 시작했다.

# docker container ls 결과에 있는 container ID를 입력
sudo docker exec -it [ContainerID] sh

파일 자체는 존재하고 있었다.

그래서 컨테이너에 접속한 상태에서 node 명령을 수행한다.

node /app/node_modules/playwright-core/cli.js install chromium

그 후에는 OpenClaw에서 사용할 browser를 설정해줘야 한다.

컨테이너 내부에서 chromium의 실행 파일의 경로를 확인한다. (아래의 결과와 같게 나올 것이다)

$ find /home/node/.cache/ms-playwright -type f \( -name chrome -o -name chromium -o -name chrome-wrapper \) | head -n 5
/home/node/.cache/ms-playwright/chromium-1208/chrome-linux64/chrome-wrapper
/home/node/.cache/ms-playwright/chromium-1208/chrome-linux64/chrome

 

해당 경로를 openclaw.json의 browser.executablePath에 등록해 준다.

$ sudo vi /root/.openclaw/openclaw.json
# 아래와 같이 설정
# 참고문서 : https://docs.openclaw.ai/tools/browser#configuration
{
  ...
  "browser": {
    "enabled": true,
    "headless": true,
    "noSandbox": true,
    "executablePath": "/home/node/.cache/ms-playwright/chromium-1208/chrome-linux64/chrome"
  },
  ...
}

 

이것으로 설치가 완료되었으면 좋겠지만, 지금 설치한 것은 playwright의 바이너리 일 뿐, 의존성 패키지들을 설치해 주어야 한다.

공식 문서에 의하면

If you need Playwright to install system deps, rebuild the image with OPENCLAW_DOCKER_APT_PACKAGES instead of using --with-deps at runtime.

Playwright에서 시스템 종속성을 설치해야 하는 경우, 런타임에 with-deps 옵션을 사용하는 대신 OPENCLAW_DOCKER_APT_PACKAGES 옵션을 사용하여 이미지를 다시 빌드하십시오.

 

라고 적혀있다.

 

몇 번의 시행착오를 통해 알게 된 필요한 의존성은 아래와 같다.

  • libnspr4
  • libnss3
  • libatk1.0-0
  • libatk-bridge2.0-0
  • libcups2
  • libxkbcommon-x11-0
  • libxcomposite1
  • libxdamage1
  • libxfixes3
  • libxrandr2
  • libgbm1
  • libasound2

위 의존성들을 포함해서 빌드를 시도한다.

# 의존성 패키지를 추가 후, 재 빌드
sudo OPENCLAW_DOCKER_APT_PACKAGES="libnspr4 libnss3 libatk1.0-0 libatk-bridge2.0-0 libcups2 libxkbcommon-x11-0 libxcomposite1 libxdamage1 libxfixes3 libxrandr2 libgbm1 libasound2" ./docker-setup.sh

# 재 빌드 후 나오는 설정은 ESC를 눌러서 취소해도 괜찮다. (이미 설정 값들이 있기 때문)

 

시행착오 과정이 궁금하다면 아래를 확인하도록 하자.

더보기

Docker Container 내부에서 openclaw browser를 시작하는 명령어를 수행하며, 에러를 확인한다.

$ openclaw browser --browser-profile openclaw start
🦞 OpenClaw 2026.3.3 (unknown)
   I keep secrets like a vault... unless you print them in debug logs again.
│
◇
Error: Error: Failed to start Chrome CDP on port 18800 for profile "openclaw".
Chrome stderr:
/home/node/.cache/ms-playwright/chromium-1208/chrome-linux64/chrome:
error while loading shared libraries:
libatk-bridge-2.0.so.0:
cannot open shared object file: No such file or directory

 

위의 로그에서 어떠한 라이브러리를 로드하다가 에러가 나왔는지 확인할 수 있다.

이걸 반복하면서, 모든 의존성을 설치 해 준다.

 

사실 검색을 하면 나올 것 같았지만, 최소한의 라이브러리만 설치하고 싶다는 생각이 있었기에, 노가다를 했다.

3) 컨테이너 재기동 후 OpenClaw가 해당 도구를 인식하는지 확인

환경변수들을 적용하기 위해서 컨테이너를 완전 종료 후 기동했다.

그리고, 브라우저 프로필이 기동 되는지 확인한다.

# 컨테이너 재기동
docker compose down
docker compose up -d

# 컨테이너에 접속
docker container ls
docker exec -it [컨테이너ID] sh

# 브라우저 프로필 기동
openclaw browser --browser-profile openclaw start

# 브라우저 프로필 상태 확인
openclaw browser status

 

의존성 패키지 시행착오는 출근길에 해도 될 것 같았어서, 휴대폰으로 작업을 했었다.

 

사진처럼 enabled, running이 true라면 문제없이 기동 된 것이다.

이것으로 준비가 완료되었고, OpenClaw가 제시한 4번은 문제가 생기면 늘려줄 예정이다.

동작 확인

Google은 너무 유명하다 보니, 내 블로그 기사 링크를 주고, 제목을 확인할 수 있는지 시켰다.

 

드디어 OpenClaw가 브라우저 조작이 가능하게 되었다.

 

한 번씩 브라우저 조작을 시키면, 답장이 돌아오지 않는 현상이 생긴다.

그래서 기본 타임아웃 값이 있는 것 같아서, 물어보고, 수정까지 시켜주었다.

 

권한을 full로 주니, 시키기만 하면 자기가 알아서 설정까지 다 해줘서 정말 세상 편하다는 걸 느꼈다.

오늘의 잡담

내가 사고 싶었던 가방은 결국 재고가 없는 것 같았다.

 

어제 직접 알아봤을 때도 재고가 없는 걸 확인했지만, OpenClaw에게 확인사살 당했다.

 

뜬금없지만, 디스코드로 OpenClaw에게 일을 시키면, 진행 중인 작업에 따라서 이모지를 찍어주는데 한 번씩은 귀엽게 느껴진다.

 

요즘 AI 툴은 많지만, 대부분은 질문에 답해주는 수준에서 끝나는 경우가 많다.
그런데 OpenClaw는 조금 결이 달랐다. 공식 사이트에서부터 아예 "The AI that actually does things (실제로 일을 하는 AI)"라고 소개하고 있었고, 메일 정리나 캘린더 관리, 각종 채팅 앱 연동까지 지원하는 개인용 AI 어시스턴트라는 점이 흥미로웠다.

 

그래서 이번에는 내 노트북에 직접 OpenClaw를 설치해 봤다.
사실 처음에는 맥미니에 설치해서 돌려볼까 생각했다. 주변에서 맥미니를 작은 서버처럼 써서 이런 AI 에이전트를 돌리는 사람들이 꽤 있었기 때문이다.

나도 잠깐 맥미니 구매를 고민했지만, 집에 거의 쓰지 않고 굴러다니던 노트북이 하나 떠올랐다. 어차피 테스트 겸 설치해 보는 거라면 새 장비를 사기보다는 이 노트북에 먼저 설치해 보는 게 낫겠다 싶었다.

그래서 결국 이번 실험(?)은 집에 있던 노트북에 OpenClaw를 설치하는 것으로 시작하게 되었다.

설치 환경

CPU Intel Core i7 10750H
GPU Intel UHD Graphics + RTX 2060
RAM 32GB
OS Ubuntu Server 24.04 LTS

 

설치 시작

OS 설치

먼저 노트북에 OS를 설치하는 것 부터 시작했다.
업무에서 사용하는 것 이외에, 라즈베리파이 같은 미니 PC가 아닌 개인용 노트북에 우분투를 설치하는 것은 처음이었다.


Windows나 Ubuntu같은 GUI 환경을 설치하지 않고, CLI환경을 설치한 이유는 최대한 가벼운 환경으로 구동하고 싶었기 때문이다.


어차피 이 노트북은 모니터와 키보드를 항상 연결해서 사용하는 장비라기보다는, 집 한쪽에 두고 서버처럼 사용할 생각이었기 때문에 꼭 GUI가 필요하지는 않을 것 같았다.


필요한 패키지 (ssh, vim, git 등등) 을 설치 하는 것으로 OS설치를 마무리 했다.



 

작업을 위해 SSH 연결

위에서 쓴 것 처럼, 노트북은 덮어둔 상태로 집 한쪽에 두고 서버처럼 이용할 생각이었다.

그래서 실제 작업용 PC에서 SSH로 Ubuntu Server에 접속해 주었다.

Docker 설치

 

Ubuntu

Jumpstart your client-side server applications with Docker Engine on Ubuntu. This guide details prerequisites and multiple methods to install Docker Engine on Ubuntu.

docs.docker.com

공식 문서의 Install에 따라서 설치해 주었다.

# Add Docker's official GPG key:
sudo apt update
sudo apt install ca-certificates curl
sudo install -m 0755 -d /etc/apt/keyrings
sudo curl -fsSL https://download.docker.com/linux/ubuntu/gpg -o /etc/apt/keyrings/docker.asc
sudo chmod a+r /etc/apt/keyrings/docker.asc

# Add the repository to Apt sources:
sudo tee /etc/apt/sources.list.d/docker.sources <<EOF
Types: deb
URIs: https://download.docker.com/linux/ubuntu
Suites: $(. /etc/os-release && echo "${UBUNTU_CODENAME:-$VERSION_CODENAME}")
Components: stable
Signed-By: /etc/apt/keyrings/docker.asc
EOF

sudo apt update

 

위의 커맨드를 실행하기만 하면 설치가 완료된다.

 

OpenClaw 설치

 

Docker - OpenClaw

Docker (optional) Docker is optional. Use it only if you want a containerized gateway or to validate the Docker flow. Is Docker right for me? Yes: you want an isolated, throwaway gateway environment or to run OpenClaw on a host without local installs. No:

docs.openclaw.ai

Docker 환경에서의 설치 방법에 대해서 공식 문서가 제공되어 있다.

 

이 문서에서 소개하는 Quick start의 순서로 아래의 명령어를 수행하라고 적혀있다.

./docker-setup.sh

 

나는 처음에 이 문서만 보고 리포지토리는 어디 있는데? 했더니, Install 문서에 적혀있었다 (...)

 

Install - OpenClaw

Install Already followed Getting Started? You’re all set — this page is for alternative install methods, platform-specific instructions, and maintenance. System requirements Node 22+ (the installer script will install it if missing) macOS, Linux, or Wi

docs.openclaw.ai

# 1. Clone and build
git clone https://github.com/openclaw/openclaw.git
cd openclaw
pnpm install
pnpm ui:build
pnpm build

 

그렇게 리포지토리를 클론 하고, 시작된 설치

 

위와 같은 화면이 나오기 시작하면서 이것저것 설정을 시작한다.

시행착오 1

설정을 완료했더니, 에러가 발생하기 시작했다.

◇ What now ───────────────────────────────────────────────────────────────╮ 
│ │ │ What now: https://openclaw.ai/showcase ("What People Are Building"). │ 
│ │ ├──────────────────────────────────────────────────────────────────────╯ 
│ └ Onboarding complete. Use the dashboard link above to control OpenClaw.
==> Docker gateway defaults
Container openclaw-openclaw-gateway-1 Starting
Container openclaw-openclaw-gateway-1 Started
Container openclaw-openclaw-cli-run-a067220028f5
Creating Container openclaw-openclaw-cli-run-a067220028f5
Created Error response from daemon: cannot join network namespace of container:
Container ddb6f3e2b2f44a8d1a835fedb9781b50dd616aaaf3da59cc07c71ece53edcdad is restarting, wait until the container is running

 

무언가의 문제로 컨테이너가 자동으로 재시작되고 있는 것 같았다.

# 로그 확인 명령어 수행
$ docker logs --tail=200 openclaw-openclaw-gateway-1

2026-03-05T14:15:28.620+00:00 Gateway failed to start:
Error: non-loopback Control UI requires gateway.controlUi.allowedOrigins (set explicit origins),
or set gateway.controlUi.dangerouslyAllowHostHeaderOriginFallback=true to use Host-header origin fallback mode

2026-03-05T14:16:31.277+00:00 Gateway failed to start:
Error: non-loopback Control UI requires gateway.controlUi.allowedOrigins (set explicit origins),
or set gateway.controlUi.dangerouslyAllowHostHeaderOriginFallback=true to use Host-header origin fallback mode

2026-03-05T14:17:33.967+00:00 Gateway failed to start:
Error: non-loopback Control UI requires gateway.controlUi.allowedOrigins (set explicit origins),
or set gateway.controlUi.dangerouslyAllowHostHeaderOriginFallback=true to use Host-header origin fallback mode

 

로그 확인 결과, allowedOrigins설정이 되어있지 않아서 발생하는 문제 같았다.

dangerouslyAllowHostHeaderOriginFallback를 true로 해도 해결이 된다고 하지만, 설정값 이름에서부터 dangerous가 붙어있으니, Origin을 설정해 주기로 했다.

 

여기서 한 가지 문제가 발생했다.

그래서 그 설정은 어디서 하는데?

 

... 또다시 검색이 시작되었다.

 

찾아보니 다들 한마디로 /home/node/.openclaw/openclaw.json에 설정 파일이 있다고 한다.

그런데 지금 나는 OpenClaw 도커 컨테이너에서 기동 중이니, docker container에 접속해서 설정할 필요가 있다.

만약 이 글을 보고 해결을 하려고 한다면 깨우침 까지는 스킵하는 걸 추천한다. (시행착오 그 자체가 담겨있다)

 

그럼 컨테이너를 자동 재시작되게 하는 것을 방지하고, 어떻게든 수정을 해야 한다.

아래와 같은 명령어로, openclaw-cli config를 이용하는 상태라면 실행하기 전 설정하는 상태에서 멈출 것이라고 예상하고, 실행에 옮겼다.

$ sudo docker compose run --rm openclaw-cli config

예상대로 설정창이 나오기 시작했다.

이 상태에서, 터미널을 추가로 기동 하고, SSH로 연결을 해서, Docker Container의 정보를 확인해 보기로 했다.

다행히 문제없이 running 상태에서 유지되는 것 같았다.

그러면 이제 해당 컨테이너에 들어가서 수정하는 것만 남았다.

이걸로 파일이 확인되었다. 여기에 값을 수정하는 것만 남았다고 생각을 해서 기쁜 마음에 vi로 수정을 하려고 했다.

어림도 없었다. 이 컨테이너에는 vim이 설치되어있지 않은 것 같았다.

그래서 sed 명령어로 설정 값을 추가해 주었다.

  "gateway": {
    "port": 18789,
    "mode": "local",
    "bind": "lan",
    "controlUi": {
      "allowedOrigins": [
        "http://192.xxx.xxx.xxx:18789",
        "http://localhost:18789",
        "http://127.0.0.1:18789"
      ]
    },

최종적으로는 이런 구조로 만들어 주었다.

지금 나의 환경은 외부에서 노트북에 있는 컨테이너로 접속을 할 예정이기 때문에, 노트북의 IP를 추가적으로 등록해 주었다.

그 후, 컨테이너를 재시작한 결과, 문제없이 running 상태가 유지되기 시작했다.

깨우침

openclaw리포지토리에는 .env파일이 존재한다.

OPENCLAW_CONFIG_DIR=/root/.openclaw
OPENCLAW_WORKSPACE_DIR=/root/.openclaw/workspace
OPENCLAW_GATEWAY_PORT=18789
OPENCLAW_BRIDGE_PORT=18790
OPENCLAW_GATEWAY_BIND=lan
OPENCLAW_GATEWAY_TOKEN=
OPENCLAW_IMAGE=openclaw:local
OPENCLAW_EXTRA_MOUNTS=
OPENCLAW_HOME_VOLUME=
OPENCLAW_DOCKER_APT_PACKAGES=
OPENCLAW_SANDBOX=
OPENCLAW_DOCKER_SOCKET=/var/run/docker.sock
DOCKER_GID=
OPENCLAW_INSTALL_DOCKER_CLI=
OPENCLAW_ALLOW_INSECURE_PRIVATE_WS=

 

 

docker-compose파일에 있는 환경변수 OPENCLAW_CONFIG_DIR는 여기에서 선언되어 있었다.

즉 내 로컬의 /root/.openclaw 경로에 설정 값이 들어가 있다는 것이다.

# Ubuntu에서 실행
$ sudo cat /root/.openclaw/openclaw.json
{
  "meta": {
    "lastTouchedVersion": "2026.3.3",
    "lastTouchedAt": "2026-03-07T02:17:41.324Z"
  },
  "wizard": {
    "lastRunAt": "2026-03-07T02:17:41.293Z",
    "lastRunVersion": "2026.3.3",
    "lastRunCommand": "configure",
    "lastRunMode": "local"
  },

문제없이 해당 값을 읽어올 수 있었다.

 

시행착오 2

gateway에 접속했을 때 발생하는 문제

http://192.xxx.xxx.xxx:18789 로 접속했더니, 아래와 같은 에러가 발생했다.

control ui requires device identity (use HTTPS or localhost secure context)

# 서버상의 로그
openclaw-gateway-1 |
2026-03-06T15:20:37.067+00:00 [ws] closed before connect conn=9xxxxxx-xxxx-xxxx-xxxx-xxxxxxxxxxx7
remote=192.xxx.xxx.xxx fwd=n/a
origin=http://192.xxx.xxx.xxx:18789
host=192.xxx.xxx.xxx:18789
ua=Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7)
AppleWebKit/537.36 (KHTML, like Gecko)
Chrome/145.0.0.0 Safari/537.36 code=1008
reason=control ui requires device identity (use HTTPS or localhost secure context)

 

Origin을 추가해도, 위와 같이 에러가 나온다.

조사해 보니, 깃허브에 버그 이슈가 있었다.

 

[Bug]: control ui requires device identity (use HTTPS or localhost secure context) · Issue #32473 · openclaw/openclaw

Bug type Regression (worked before, now fails) Summary I'm using a Hostinger VPS and Docker, and after configuring the Brave key, I'm receiving the reported error. control ui requires device identi...

github.com

아직 대응은 되어있지 않은 것 같지만, 원인 자체는 LAN 주소의 평문 HTTP에서는 “device identity”를 만들 수 없어서, OpenClaw Control UI의 WebSocket 연결을 게이트웨이가 1008로 끊는 상황이었다.

 

그래서 가장 간단한 해결 방법으로 localhost로 접속을 하면 해결이 된다.

SSH 터널로 localhost로 접속하면 가능할 것이라 예상했고, 그 결과 문제없이 접속되었다.

ssh -L 18789:127.0.0.1:18789 username@192.xxx.xxx.xxx

다른 에러가 발생하지만, 이건 Gateway설정 시에 넣었던 토큰값을 넣어주면 해결될 문제다.

시행착오 3

첫 설정 때 문제없다고 생각했었지만, 실제로 기동 된 후 문제가 있음을 알게 되었다.

 

Agent 연동이 되어있지 않아서 생기는 문제였다.

 

처음 설정에서 OpenAI OAuth 연동 시, Fetch Failed라는 에러가 나오는 문제가 있었다.

 

이 문제에 대해서는 사진이 없지만, OAuth 연동을 하게 되면, Callback URL을 붙여 넣기 해달라고 한다.

아무런 작업 없이, 붙여 넣으면, Fetch Failed라는 에러가 나오면서 연동이 제대로 되지 않는다.

 

이 문제 또한 시행착오 2와 같은 방식으로 터널링을 해 주는 것으로 해결할 수 있다.

Callback URL에 들어가 있는 포트 번호를 개방해 주는 방식으로, 해결할 수 있다.

ssh -L 포트번호:127.0.0.1:포트번호 username@192.xxx.xxx.xxx

 

잡담

아직 초기설정을 마친 단계라서 아무런 스킬 / 권한이 등록되어있지 않은 상태라서 바보 그 자체를 보여준다.

 

기본적인 설정만 끝낸 상태라서 OpenClaw가 제대로 일을 하는 단계는 아니다.

앞으로 어떤 식으로 활용할 수 있을지 조금 더 실험해 볼 생각이다. (그런데 시행착오를 곁들인)

Android Developers 문서를 따르면 Wear OS에서 Jetpack Compose를 사용하는 것을 권장하고 있다.

그리고 Android Studio 환경에서 Empty Wear App으로 프로젝트를 생성 시 Compose 방식으로 생성된다.

Android Studio Wear OS 프로젝트 생성 화면

 

이렇게 생성된 프로젝트의 MainActivity를 확인 해 보면 @Preview로 되어있는 코드가 있고, 이를 통해 Design을 확인할 수 있다.

 

@Preview(device = Devices.WEAR_OS_SMALL_ROUND, showSystemUi = true)
@Composable
fun DefaultPreview() {
    WearApp("Preview Android")
}

 

위 방법으로만으로도 충분하다고 생각할 수 있지만, 크기가 다른 디바이스나 사각형 디스플레이를 가진 디바이스또한 신경을 써서 개발하는 것이 바람직하다.

 

@Preview를 추가로 작성하는것도 괜찮은 방법이지만 더욱 간단하게 하는 방법이 있다.

바로 공식 문서의 Codelab쪽에서도 사용중인 방법으로 @WearPreviewDevices를 사용하는 방법이다.

이를 사용하면 사각형 디스플레이, 원형, 원형 작은 사이즈 디바이스의 Preview를 동시에 확인할 수 있다.

 

@WearPreviewDevices는 기본 프로젝트에는 포함되지 않은 모듈이기에 따로 추가 해 주는 작업이 필요하다.

 

개발하려는 wear의 build.gradle쪽에 "androidx.wear.compose:compose-ui-tooling"을 추가 해 주어야 한다.

...
dependencies {
...
    implementation ("androidx.wear.compose:compose-ui-tooling:1.2.1")
}

포스팅 하는 시점에서는 1.2.1 버전이 최신 stable 버전이었기에 사용하였다.

 

의존성을 추가했다면 @Preview 부분을 변경한다.

// Before : @Preview(device = Devices.WEAR_OS_SMALL_ROUND, showSystemUi = true)
@WearPreviewDevices
@Composable
fun DefaultPreview() {
    WearApp("Preview Android")
}

WearPreviewDevices로 변경 후의 Design 모습

+ Recent posts