콘텐츠로 이동
Study NoteAgent 배포 플랫폼

WebMCP — 웹사이트가 AI에게 사용법을 알려 주는 방법

결론부터
  • WebMCP는 웹 페이지의 기능과 입력 규칙을 AI가 발견하고 호출할 수 있는 도구로 공개하는 방법이다.
  • Playwright MCP를 쓰는 Codex는 지원되는 같은 브라우저·탭에서 browser_evaluate로 getTools()·executeTool()을 실행해 도구를 사용한다.
  • 도구는 사이트가 직접 제공하거나 우리가 확장으로 덧붙일 수 있다. 도구 등록과 AI의 브라우저 연결은 별도로 준비해야 한다.
  • AI가 도구를 고르면 페이지가 준비된 코드를 실행한다. 업무 API를 호출할 때도 서버의 로그인·사용자 권한 검사는 계속 필요하다.
  • WebMCP 도구는 실행 중인 브라우저 페이지에 있다. 브라우저 없이 업무 API를 쓰는 서버 Agent에는 MCP 서버 같은 별도 연동이 필요하다.

로컬에서 쓰는 Codex에 **“회의실 사이트에서 4명이 쓸 수 있는 방을 찾아줘”**라고 부탁했다고 하자. Codex가 Playwright MCP로 브라우저에 연결되어 있다면 입력칸을 채우고 검색 버튼을 누를 수 있다. 사이트가 WebMCP 도구도 제공하면, Codex는 search_rooms라는 기능과 capacity라는 입력 규칙을 읽고 그 도구를 호출하는 경로를 사용할 수 있다.

Codex가 판단하고, Playwright MCP가 브라우저로 전달하고, 페이지가 검색 코드를 실행한다. 이 페이지는 이미 Codex로 브라우저 작업을 맡기는 사용자를 위해 WebMCP 도구를 쓰려면 무엇을 연결하고 어떤 코드를 실행해야 하는지 설명한다. 읽고 나면 브라우저 연결, 도구 발견, 실제 업무 실행을 구분하고 연결이 끊긴 지점을 찾을 수 있다.

먼저 Codex에서 호출하는 쪽을 보고, 뒤에서 사이트가 도구를 등록하는 쪽을 설명한다. 사이트를 고칠 수 없다면 브라우저 확장으로 도구 덧붙이기를 함께 본다.

이 장에서 처음 나오는 말4개
WebMCPWeb Model Context Protocol
웹 페이지의 기능을 AI가 발견하고 호출할 수 있는 도구로 공개하는 브라우저 API 제안이다.
도구Tool
AI가 이름과 입력값으로 호출할 수 있게 공개한 기능이다. 이 예에서는 회의실 검색이다.
브라우저 AIBrowser Agent
브라우저의 페이지와 연결되어 사용자 요청을 수행하는 AI다. 여기서는 Playwright MCP를 쓰는 Codex가 이 역할을 맡는다. 모델 자체는 외부 서버에서 실행될 수도 있다.
Playwright MCPPlaywright MCP
Codex 같은 MCP client에 브라우저 조작과 페이지 JavaScript 실행 도구를 제공하는 서버다.

브라우저 AI는 특정 제품명이나 모델의 실행 위치가 아니라 페이지를 사용하는 에이전트의 역할이다. Playwright를 통해 탭을 조작하는 로컬 Codex도 포함된다. 사이트에 채팅창을 넣어야만 사용할 수 있는 것은 아니다.

AI가 제공되는 형태페이지와 만나는 방식
로컬 Codex + Playwright MCP브라우저 조작 도구로 대상 탭에 연결하고 페이지 JavaScript 실행 기능으로 WebMCP 호출
브라우저 내장 AI·AI 확장해당 구현이 제공하는 WebMCP 도구 발견·호출 기능 사용
사이트 운영자가 넣은 AI 채팅 패널페이지 또는 iframe의 에이전트가 허용된 WebMCP 도구를 사용하도록 구현

공식 제안은 브라우저 내장 AI와 페이지·iframe에 넣은 에이전트를 모두 다룬다. 아래 Codex 예는 Playwright의 페이지 실행 기능과 WebMCP API를 조합하는 방식이며, Codex 자체의 WebMCP 자동 발견 기능을 전제하지 않는다.

브라우저 agent는 화면을 보고 추측한다

섹션 제목: “브라우저 agent는 화면을 보고 추측한다”

웹사이트가 도구를 제공하지 않으면 AI는 화면 이미지나 DOM(페이지 요소의 구조), 접근성 정보를 읽고 입력칸과 버튼을 찾아 조작할 수 있다. 이 방식도 가능하지만 화면 구성이 바뀌면 다시 해석해야 한다.

WebMCP 제안은 사이트가 가능한 동작과 입력 규칙을 직접 알려 주는 방법을 추가한다. Google·Microsoft가 제안했으며 W3C Web Machine Learning Community Group에서 논의 중이다.

같은 요청화면을 읽고 조작할 때WebMCP 도구를 쓸 때
기능 찾기“이 칸이 인원수이고, 저 버튼이 검색이겠구나”“search_rooms는 회의실 검색이라고 적혀 있구나”
값 전달입력칸을 찾아 4를 채우고 버튼 클릭capacity: 4로 도구 호출
실제 검색버튼에 연결된 사이트 코드가 실행도구에 연결된 사이트 코드가 실행
결과 확인화면을 다시 읽어 결과 파악사이트 코드가 반환한 결과를 받음

사이트가 제공하는 기능은 같고, AI가 그 기능을 찾아 호출하는 길이 추가된다. 도구가 없는 동작은 여전히 화면 조작이 필요할 수 있다. WebMCP가 모든 버튼을 자동으로 도구로 바꾸거나 AI 모델을 사이트에 설치해 주는 것은 아니다.

이 경로에서 MCP와 WebMCP는 서로 다른 구간에 있다. Codex는 MCP로 Playwright의 도구를 호출하고, Playwright는 브라우저 안에서 WebMCP API를 실행한다.

구간전달하는 것실행하는 쪽
Codex → Playwright MCPbrowser_evaluate에 전달할 JavaScriptPlaywright가 선택된 탭으로 전달
선택된 탭 → WebMCPgetTools()로 목록 조회, executeTool()로 호출브라우저가 페이지에 등록된 도구 실행
페이지 → 업무 서버기존 회의실 검색 HTTP 요청서버가 로그인·권한 검사 후 데이터 반환

Playwright MCP의 browser_evaluate는 페이지에서 JavaScript를 실행하는 도구다. 이 기능이 이미 연결되어 있으면 별도의 WebMCP 중계 서버를 새로 만들 필요는 없다. 페이지의 search_rooms가 Codex의 MCP 도구 목록에 자동 등록되는 것은 아니며, 여기서는 browser_evaluate로 목록을 읽고 호출한다.

같은 브라우저와 탭을 준비한다

섹션 제목: “같은 브라우저와 탭을 준비한다”
  1. Codex에 Playwright MCP를 등록한다. 설치는 Playwright 공식 설정 안내와 Codex MCP 문서를 따른다. 아래는 로컬 Codex의 ~/.codex/config.toml에 둘 연결 설정 예다. 이미 등록했다면 중복 추가하지 않는다.

    [mcp_servers.playwright]
    command = "npx"
    args = ["-y", "@playwright/mcp@latest", "--browser", "chrome"]

    codex mcp list로 등록을 확인한다. 이 확인은 서버 설정 확인이며 브라우저 연결·WebMCP 지원까지 증명하지 않는다. 예제는 공식 안내의 @latest를 쓰므로, 반복 검증할 때는 실제 사용한 패키지·브라우저 버전을 기록한다.

  2. Playwright가 사용할 Chrome에서 WebMCP를 활성화한다. 로컬 실험은 Chrome 안내의 chrome://flags/#enable-webmcp-testing을 켜고 해당 브라우저를 재시작한다. 평소 쓰는 Chrome에만 켜고 Playwright의 다른 프로필도 준비됐다고 생각하면 안 된다. 아래 예는 document.modelContext.getTools()와 객체 인자를 받는 executeTool()을 지원하는 버전을 전제로 한다.

  3. 도구가 등록된 페이지를 열고 그 탭을 선택한다. Playwright의 browser_navigate·browser_tabs로 회의실 페이지를 열거나 선택하고, 그 브라우저 세션에서 필요한 로그인을 마친다. 이미 로그인한 기존 Chrome 탭에 연결하려면 Playwright 확장 연결을 따른다. 이 경우 Playwright 확장을 설치하고 실행 인자에 --extension을 사용한다. 이 확장은 Codex와 브라우저를 연결하며, 사이트에 회의실 도구를 주입하는 확장과는 역할이 다르다.

설정을 되돌리려면 추가한 mcp_servers.playwright 항목을 제거하고 Codex 세션을 다시 시작한다. 실험용 Chrome 플래그도 원래 값으로 복원한 뒤 재시작한다.

도구 설명을 읽고 검색을 호출한다

섹션 제목: “도구 설명을 읽고 검색을 호출한다”

아래 두 코드는 Codex가 Playwright MCP의 browser_evaluate 도구에 function 값으로 전달할 JavaScript다. 사이트 소스에 붙이는 코드가 아니다. 뒤의 명령형 예제처럼 search_rooms를 등록한 페이지를 가정한 설명용 발췌이며, 실제 Codex·브라우저 통합 실행을 검증한 예제는 아니다.

먼저 지원 여부와 도구 목록을 읽는다.

async () => {
const context = document.modelContext;
if (typeof context?.getTools !== 'function' ||
typeof context?.executeTool !== 'function') {
throw new Error('이 탭에서 필요한 WebMCP API를 사용할 수 없습니다.');
}
const tools = await context.getTools();
return {
url: location.href,
tools: tools.map(({ name, description, inputSchema, origin }) => ({
name, description, inputSchema, origin,
})),
};
}

예상 결과에는 현재 탭 URL과 search_rooms의 설명, capacity가 1 이상의 정수라는 입력 규칙이 있다. getTools() 결과의 window 같은 브라우저 객체는 밖으로 전달하지 않고 필요한 필드만 반환한다. 이 시점에는 검색이 실행되지 않는다. Codex는 반환된 설명을 읽고 사용자 요청에 맞는 도구와 인자를 고른다.

다음은 같은 탭에서 capacity: 4로 검색하는 호출이다. 도구 객체는 호출 시 페이지 안에서 다시 찾는다.

async () => {
const context = document.modelContext;
const tools = await context.getTools();
const tool = tools.find(t =>
t.name === 'search_rooms' && t.origin === location.origin
);
if (!tool) throw new Error('현재 사이트의 회의실 검색 도구가 없습니다.');
return await context.executeTool(tool, { capacity: 4 });
}

조회·호출 형식은 Chrome의 발견·실행 API를 따른다. 서버가 한라실·정원 6명을 반환하는 예라면, 페이지는 결과를 표시하고 browser_evaluate도 [{"name":"한라실","capacity":6}]라는 JSON 문자열을 Codex에 돌려준다. 검색 결과가 없으면 빈 목록이고, 권한·네트워크 오류는 호출 실패다. 예약 완료로 해석하지 않는다.

Codex에 줄 요청은 다음처럼 구체화할 수 있다.

Playwright MCP로 회의실 탭을 선택하고 URL을 확인해. browser_evaluate로 WebMCP 도구 목록과 입력 규칙을 읽은 뒤, 현재 사이트의 search_rooms에 capacity 4를 전달해 검색 결과를 알려줘.

관찰한 결과먼저 확인할 곳
browser_evaluate를 쓸 수 없음Codex의 Playwright MCP 연결과 도구 허용 설정
getTools·executeTool이 없음실제 연결된 브라우저의 버전·플래그·페이지 기능 허용 조건
도구 목록이 비었거나 search_rooms가 없음현재 URL·탭, 페이지의 등록 완료 여부, iframe의 origin과 공개 범위
검색 호출에서 로그인·권한 오류그 브라우저 세션의 로그인과 업무 서버의 권한 검사
페이지 이동 뒤 기존 도구를 찾지 못함새 문서에서 목록을 다시 조회. 이전 페이지의 도구가 남아 있다고 가정하지 않음

playwright-cli와 스킬로도 같은 경로를 쓴다

섹션 제목: “playwright-cli와 스킬로도 같은 경로를 쓴다”

playwright-cli의 eval도 페이지 JavaScript를 실행한다. 따라서 Codex가 CLI를 실행할 수 있으면 위 함수들을 eval로 전달하는 방식으로 연결할 수 있다. 이 경우 Codex → CLI → 탭의 WebMCP API 경로이며 Playwright MCP 서버는 필수가 아니다.

스킬은 “탭 확인 → API 확인 → 도구 설명 읽기 → 입력 구성 → 호출 → 결과 확인” 절차를 Codex에 알려 주는 문서다. 일반 Playwright 사용법만 담은 스킬이 WebMCP 호출 절차까지 자동으로 제공하지는 않는다. WebMCP를 활성화하거나 사이트에 도구를 등록하는 작업도 별도로 필요하다.

회의실 검색을 한 단계씩 따라가기

섹션 제목: “회의실 검색을 한 단계씩 따라가기”

아래에서 다음을 누르며 화살표와 각 구성 요소의 상태를 보자. 특히 도구 호출, 서버 요청, 권한 검사는 서로 다른 단계다.

아래의 AI는 앞에서 연결한 Codex다. Codex와 페이지 사이의 화살표에는 Playwright MCP를 통한 전달이 포함된다. 사이트 개발자가 도구를 제공하고, 로그인한 사용자가 같은 사이트의 회의실 API를 쓰는 설명용 예다. 실제 AI나 WebMCP를 실행하지 않으므로 실험 기능을 켤 필요가 없다. 처음으로 돌아가거나 전체 흐름을 펼쳐 비교할 수 있다.

회의실 검색: Codex가 고르고, 페이지가 실행하고, 서버가 권한을 확인한다

각 단계가 끝난 시점의 보관 상태입니다. 강조된 객체 사이의 화살표를 따라 전달 값을 읽으세요. 내부 처리는 같은 객체로 돌아옵니다.

구성 요소의 역할
웹 페이지
Playwright MCP로 연결한 탭의 회의실 앱. 검색 도구의 실행 코드가 여기에 있다. 그림에서는 Playwright MCP와 브라우저의 전달 경로를 화살표에 포함한다.
Codex
사용자 요청을 받아 도구와 입력값을 고른다. Playwright MCP의 browser_evaluate로 페이지의 WebMCP API를 실행한다. 모델 자체는 외부 서버에서 실행될 수도 있다.
업무 서버
로그인과 조회 권한을 검사하고 회의실 데이터를 돌려준다. 기존 웹 앱의 서버다.

1. 페이지가 검색 도구를 준비한다

웹 페이지 → 웹 페이지
도구 등록 · registerTool로 검색 기능 공개처리 내용: search_rooms

사용자가 회의실 앱에 로그인해 페이지를 열었다. 페이지 코드가 search_rooms의 이름·설명·입력 규칙·실행 함수를 브라우저에 등록한다. 등록만으로 검색이 실행되지는 않는다.

웹 페이지
검색 실행 코드와 등록한 도구 정의. 조회 결과는 아직 없다.
Codex
사용자의 요청: “4명이 쓸 수 있는 회의실을 찾아줘.” 아직 도구 목록을 읽지 않았다.
업무 서버
기존 사용자 세션과 회의실 데이터. 새 검색 요청은 없다.

2. AI가 도구 설명을 읽는다

웹 페이지 → Codex
도구 발견 결과 · Playwright MCP를 통해 getTools 결과 전달주요 전달 값: search_rooms · capacity: 인원수

Codex가 browser_evaluate로 페이지의 getTools()를 실행해 받은 결과다. 도구의 이름·설명·입력 규칙을 보고 search_rooms의 capacity에 인원수를 넣는다는 것을 안다. 실행 함수 자체를 받거나 Codex의 MCP 도구 목록에 search_rooms를 자동 등록하는 과정은 아니다.

웹 페이지
등록된 도구와 실행 코드. 조회 결과는 아직 없다.
Codex
사용자 요청과 도구 설명. capacity에 4를 넣어 호출할 수 있다.
업무 서버
기존 사용자 세션과 회의실 데이터. 아직 검색 요청은 없다.

3. AI가 이름과 입력값으로 호출한다

Codex → 웹 페이지
WebMCP 호출 · 브라우저가 페이지의 execute를 실행주요 전달 값: search_rooms · capacity: 4

Codex가 browser_evaluate에 executeTool 호출 코드를 전달한다. 페이지 안에서 search_rooms 도구를 찾아 capacity: 4를 넘기면 브라우저가 등록된 execute를 실행한다. 조회·호출 코드는 Codex가 전달하지만 실제 검색 로직은 사이트가 준비한 코드다.

웹 페이지
실행 중인 검색 함수와 입력값 capacity: 4.
Codex
보낸 도구 호출. 결과를 기다린다.
업무 서버
기존 사용자 세션과 회의실 데이터. 아직 검색 요청은 없다.

4. 페이지가 평소의 검색 API를 부른다

웹 페이지 → 업무 서버
기존 HTTP 요청 · 회의실 조회 API 호출주요 전달 값: 인원수 4 · 세션 cookie

execute 안에서 같은 사이트의 /api/rooms?capacity=4로 fetch 요청을 보낸다. 이 예는 cookie로 로그인하는 앱이며, 브라우저가 기존 세션 cookie를 붙인다. 세션 cookie를 AI에게 넘기는 단계는 없다.

웹 페이지
capacity: 4로 조회 중. 서버 응답을 기다린다.
Codex
도구 결과를 기다린다. 이 예에서 로그인 cookie를 전달받지 않는다.
업무 서버
도착한 조회 요청과 cookie. 세션 유효성과 권한은 아직 검사 전이다.

5. 서버가 사용자 권한을 확인한다

업무 서버 → 업무 서버
서버 내부 검사 · 기존 세션과 조회 권한 확인처리 내용: 로그인 확인 · 조회 허용

업무 서버가 유효한 로그인인지, 이 사용자가 회의실을 조회할 수 있는지 검사한다. 여기서는 통과했다고 가정한다. 실패하면 오류를 반환해야 하며, WebMCP 호출이라는 이유로 검사를 건너뛰지 않는다.

웹 페이지
검색 요청 후 응답을 기다린다.
Codex
도구 결과를 기다린다.
업무 서버
이 요청의 사용자·권한 검증 완료. 4명 이상 회의실을 조회한 결과: 한라실, 정원 6명.

6. 서버가 검색 결과를 돌려준다

업무 서버 → 웹 페이지
HTTP 응답 · 조건에 맞는 회의실 데이터주요 전달 값: 한라실 · 정원 6명

서버가 페이지에 한라실 정보를 반환한다. 페이지 코드는 이 결과로 화면을 갱신하고 도구 반환값을 준비한다. 화면 갱신도 앱 개발자가 구현하는 동작이며 WebMCP가 자동으로 만들어 주지 않는다.

웹 페이지
검색 결과와 갱신된 화면: 한라실, 정원 6명.
Codex
아직 도구 결과를 기다린다.
업무 서버
원래 회의실 데이터와 사용자 세션. 검색만 했으므로 예약 상태는 바뀌지 않았다.

7. AI가 결과를 받아 사용자에게 답한다

웹 페이지 → Codex
도구 결과 · execute의 반환값 전달주요 전달 값: 한라실: 6명

execute의 반환값이 executeTool과 browser_evaluate의 결과로 Codex에 전달된다. Codex는 “4명이 쓸 수 있는 한라실이 있어요. 정원은 6명이에요”라고 답할 수 있다. 회의실 검색 완료는 예약 확정이 아니다. 날짜별 빈 시간 조회나 실제 예약에는 별도 기능이 필요하다.

웹 페이지
한라실을 보여 주는 검색 화면. 사용자가 이어서 조작할 수 있다.
Codex
검색 결과: 한라실, 정원 6명. 예약은 수행하지 않았다.
업무 서버
원래 회의실 데이터와 사용자 세션. 예약 변경 없음.

공식 흐름 설명에서도 페이지 코드가 필요에 따라 서버 API를 부르고 화면을 갱신한 뒤 결과를 돌려준다. 여기서 기억할 것은 AI는 무엇을 호출할지 고르고, 페이지는 준비된 코드를 실행하며, 업무 서버는 권한과 데이터를 관리한다는 역할 분담이다. 도구가 화면의 색상만 바꾸는 기능이라면 서버 요청 없이 페이지 안에서 끝날 수도 있다.

사이트가 제공하지 않으면 확장으로 덧붙인다

섹션 제목: “사이트가 제공하지 않으면 확장으로 덧붙인다”

회의실 사이트를 고칠 수 없어도 우리 브라우저에서 그 페이지에 추가 코드를 실행할 수 있다. 확장이 URL에 맞는 코드를 넣고, 그 코드가 search_rooms 같은 도구를 등록하는 방식이다. Brave의 WebMCP 구현에도 URL별 스크립트를 주입해 도구를 등록하는 사례가 있다.

사이트가 직접 제공우리가 확장으로 제공
도구 코드는 어디서 오는가?사이트가 배포하는 페이지 코드우리 확장이 페이지에 넣는 코드
실제 기능과 어떻게 연결하는가?사이트의 기존 내부 함수 등을 재사용화면의 입력칸·버튼·결과나 접근 가능한 API를 이용
사이트가 바뀌면 누가 고치는가?사이트 개발자연결 코드를 만든 우리

AI에게는 하나의 검색 도구로 보이지만, 그 안에서는 우리가 작성한 “입력칸 채우기 → 버튼 누르기 → 새 결과 기다리기 → 결과 읽기”가 실행될 수 있다. 원래 사이트의 배포 파일은 바뀌지 않고, 확장을 설치한 브라우저에만 도구가 추가된다.

도구 등록만으로 로컬 AI와 연결되는 것은 아니다. AI가 해당 브라우저·탭의 도구를 발견하고 호출하는 연결도 필요하다.

사이트 개발자는 JavaScript 함수로 도구를 등록하거나 기존 HTML form에 도구 설명을 붙인다. 둘 다 “AI가 이 기능의 이름과 입력을 알게 한다”는 목적은 같다.

명령형 — script가 도구를 등록한다

섹션 제목: “명령형 — script가 도구를 등록한다”

registerTool은 기능 안내와 실행 코드를 묶어 등록하는 함수다. 공식 JavaScript API의 구조를 회의실 예로 바꾸면 다음과 같다.

아래는 회의실 앱의 페이지 script에 들어갈 설명용 발췌다. WebMCP를 지원하고 기능이 활성화된 브라우저, 기존 /api/rooms API, 화면 갱신 함수 renderRooms가 있다고 가정한다. 이 문서에서 그대로 실행하는 코드는 아니다.

await document.modelContext.registerTool({
name: 'search_rooms',
description: '주어진 인원수 이상을 수용하는 회의실을 검색한다. 예약하지 않는다.',
inputSchema: {
type: 'object',
properties: {
capacity: { type: 'integer', minimum: 1, description: '사용 인원수' },
},
required: ['capacity'],
},
execute: async ({ capacity }) => {
const response = await fetch(`/api/rooms?capacity=${encodeURIComponent(capacity)}`);
if (!response.ok) throw new Error('회의실 조회에 실패했습니다.');
const rooms = await response.json();
renderRooms(rooms); // 기존 앱이 제공하는 화면 갱신 함수
return JSON.stringify(rooms); // AI에게 돌려줄 검색 결과
},
});
코드쉬운 뜻
name호출할 기능의 이름: search_rooms
descriptionAI가 기능을 고를 때 읽는 설명
inputSchema입력 규칙: capacity에 1 이상의 정수가 필요하다
execute호출받았을 때 페이지가 실제로 실행할 코드

입력이 {"capacity": 4}이고 서버 응답이 [{"name":"한라실","capacity":6}]이면, 화면에는 한라실이 나타나고 AI도 그 검색 결과를 받는다. 도구를 등록할 때는 검색하지 않고, 호출될 때 execute가 실행된다.

이 예의 fetch는 같은 사이트로 요청하므로 기존 로그인 cookie를 사용할 수 있다. 다른 사이트의 API까지 인증이 자동으로 해결되는 것은 아니며, 요청 대상과 앱의 인증 방식에 따라 처리가 달라진다.

선언형 — 기존 form에 attribute를 붙인다

섹션 제목: “선언형 — 기존 form에 attribute를 붙인다”

이미 인원수 입력칸과 검색 버튼이 있다면 선언형 API로 form에 도구 이름과 설명을 붙일 수 있다. 브라우저는 form 필드를 바탕으로 AI에게 보여 줄 입력 규칙을 만든다.

아래도 기존 회의실 앱의 form을 가정한 설명용 발췌다. /rooms 검색 결과 페이지가 있다는 전제다.

<form action="/rooms" method="get"
toolname="search_rooms"
tooldescription="인원수에 맞는 회의실을 검색한다. 예약하지 않는다.">
<label>
사용 인원수
<input type="number" name="capacity" min="1" required
toolparamdescription="사용 인원수">
</label>
<button type="submit">회의실 검색</button>
</form>

toolname은 기능 이름, tooldescription은 기능 설명, toolparamdescription은 입력값 설명이다. 제안 문서의 제출 규칙에 따르면 위 form은 AI가 값을 채운 뒤 사용자가 제출 버튼을 눌러야 검색된다. form에 toolautosubmit을 추가하면 사용자의 버튼 클릭을 기다리지 않고 제출할 수 있다.

이 차이는 선언형 form의 제출 규칙이다. JavaScript 도구까지 모두 자동으로 사람의 확인을 받는다는 뜻은 아니다.

둘 다 “이름과 입력 규칙을 가진 도구”를 AI에게 제공하지만 실행 코드가 있는 곳이 다르다. MCP 프로토콜의 서버 연결을 떠올리고 비교하면 된다.

질문서버 MCPWebMCP
검색 코드의 진입점은 어디에 있는가?MCP 서버 프로세스 또는 HTTP endpoint열려 있는 웹 페이지의 코드
어떻게 호출하는가?MCP client가 stdio·Streamable HTTP 등으로 서버에 요청브라우저가 페이지에 등록된 함수를 실행하거나 form을 처리
웹 페이지가 꼭 필요한가?필요 없다페이지를 실행하는 브라우저 환경이 필요하다
누구의 권한으로 업무 API를 쓰는가?연동 설계에 따라 사용자 위임 또는 서비스 신원이 예에서는 웹 앱의 기존 사용자 로그인
회의실 앱에 붙이면 무엇이 생기는가?서버 Agent가 연결할 수 있는 도구 경로해당 페이지와 연결된 AI가 사용할 도구 경로

회의실 앱이 WebMCP를 붙였다고 사내 서버 Agent에 도구가 자동 등록되지는 않는다. 서버 Agent가 브라우저 없이 업무 API를 사용해야 한다면 MCP 서버 같은 별도 연동이 필요하다.

“서버 측 Agent는 절대 WebMCP를 사용할 수 없다”로 외울 필요는 없다. 브라우저를 제어하는 연결 계층을 추가할 수는 있지만, 이때도 페이지를 실행하는 브라우저가 필요하다. 제안의 범위도 기존 서버 연동과의 보완 관계를 설명한다. 반대로 브라우저 AI가 MCP client 기능을 별도로 갖고 있다면 서버 MCP도 사용할 수 있다.

보안 모델은 origin 경계 위에 있다

섹션 제목: “보안 모델은 origin 경계 위에 있다”

회의실 검색 도구를 호출할 수 있다고 해서 모든 회의실을 예약할 권한까지 생기지는 않는다. 서로 다른 두 검사를 나누면 이해하기 쉽다.

검사이 예에서 묻는 것담당
도구 접근이 페이지의 도구를 발견하고 호출해도 되는가?브라우저의 사이트 경계와 기능 허용 설정
업무 권한로그인한 사용자가 이 회의실을 조회·예약해도 되는가?기존 업무 서버

origin은 프로토콜·호스트·포트로 구분하는 웹의 사이트 경계다. Chrome의 접근 규칙은 다른 origin에 도구를 공개할 때 exposedTo, 상대 도구를 조회할 때 fromOrigins를 명시하도록 한다. iframe의 기능 사용은 tools Permissions Policy로 통제한다. 즉 브라우저 기능을 어느 페이지에 허용할지도 정해야 한다.

업무 서버의 로그인·권한 검사는 계속 필요하다. UI에서 버튼을 숨기거나 도구 설명에 “관리자 전용”이라고 적는 것만으로 권한이 생기거나 제한되지 않는다. 이 덱의 도구 실행 권한과 같은 구분이다.

구현할 때 확인할 세부 API와 힌트
  • getTools()는 접근 가능한 도구 목록을 조회하고, executeTool()은 선택한 도구를 호출한다. toolchange는 목록이 바뀌었음을 알리는 이벤트다.
  • annotations의 readOnlyHint는 읽기 전용, consequentialHint는 중요한 결과를 만드는 동작, untrustedContentHint는 신뢰할 수 없는 내용이 결과에 포함됨을 알리는 힌트다. 힌트가 서버의 권한 검사나 악성 지시 방어를 대신하지 않는다.
  • tools Permissions Policy의 기본값은 self다. 다른 origin의 iframe에서 등록하려면 부모의 allow="tools" 같은 명시적 허용이 필요하다.
  • document.domain으로 origin 경계를 느슨하게 한 문서에서는 WebMCP API가 비활성화된다.

상세 조건은 JavaScript API와 보안·권한 조건을 확인한다.

이 덱은 서버에서 실행되는 사내 Agent 플랫폼을 설계한다. WebMCP가 들어왔을 때도 다음처럼 역할을 나누면 된다. 아래는 WebMCP의 필수 구조가 아니라 이 덱의 설계 적용안이다.

하고 싶은 일연결할 곳권한 검사
직원의 브라우저 AI가 회의실 웹 앱을 사용웹 페이지에 WebMCP 도구 추가회의실 앱 서버가 기존 사용자 권한 검사
사내 서버 Agent도 회의실 검색을 사용같은 업무 API 앞에 MCP 서버 제공플랫폼의 도구 사용 정책과 업무 API의 권한 검사
브라우저 AI가 사내 포털의 Agent를 호출포털 페이지에 Agent 호출 도구 추가포털 서버가 기존 Grant(호출 허용 규칙) 검사

같은 검색 기능을 양쪽에서 제공한다면 업무 규칙은 서버에 한 번 두고, 웹 페이지의 도구와 MCP 서버가 그 API를 각각 부르게 할 수 있다. 서버 도구의 등록·검증·공개는 사용자 MCP 관리를 따른다. WebMCP라는 이유로 이 덱에 새 도메인 객체를 추가하지는 않는다.

2026년 9월 29일 제안 저장소의 구현 현황을 확인했다. 아직 변할 수 있는 API이며 완성된 공통 웹 표준으로 가정하지 않는다.

구현공식 현황에 적힌 상태
Chrome149부터 origin trial. 로컬 실험은 chrome://flags/#enable-webmcp-testing
Edge150부터 origin trial
BraveLeo 채팅에서 실험적 지원
ChatGPT Desktop지원으로 기재
Firefox · Safari표준 입장 논의 링크가 있으며 구현 지원은 기재되지 않음

origin trial은 정식 출시 전 기능을 참여 사이트에서 시험하는 제도다. 현재 API 예제는 document.modelContext를 사용한다. 초기 자료에서 보던 navigator.modelContext와 혼동하지 않는다. 선언형 제안에는 form 제약을 입력 규칙으로 바꾸는 세부 알고리즘도 아직 미정으로 남아 있다.

회사가 브라우저 AI 사용을 허용하고, 사내 웹 앱에 **“AI가 이 화면을 제대로 사용하게 해 달라”**는 요구가 생기면 검토할 만하다. 서버 Agent만 업무 API를 호출하면 되는 상황에서는 우선 서버 연동을 보면 된다.

실제 도입 전에는 대상 브라우저의 지원 상태, 웹 앱 서버의 기존 권한 검사, 서버 MCP와의 업무 로직 공유를 확인한다. 이 페이지의 설명용 흐름은 사내 도입 결정이나 실제 제품 동작 검증을 뜻하지 않는다.

Codex에서 Playwright로 버튼을 누를 수 있다. search_rooms도 자동으로 Codex의 도구 목록에 생길까?

답과 이유

아니다. 이 예에서 Codex가 직접 호출하는 MCP 도구는 browser_evaluate다. 그 도구로 페이지의 getTools()를 실행해 설명을 읽고, executeTool()로 search_rooms를 호출한다. 사이트 도구를 Codex의 MCP 도구 목록에 직접 노출하려면 그런 기능을 제공하는 별도 중계 구현이 필요하다.

회의실 사이트가 search_rooms를 등록했다. 사내 서버 Agent도 바로 호출할 수 있을까?

답과 이유

자동으로 연결되지는 않는다. 이 도구는 브라우저에서 실행 중인 페이지에 있다. 브라우저 없이 사용하는 서버 Agent에는 MCP 서버 같은 별도 연동이 필요하다.

AI가 검색 결과로 한라실을 받았다. 회의실 예약까지 완료된 것일까?

답과 이유

아니다. search_rooms는 정원에 맞는 회의실을 조회했을 뿐이다. 실제 예약에는 날짜·시간 등의 입력과 예약 기능이 필요하고, 업무 서버가 예약 권한도 검사해야 한다.