방 안에 Agent가 있으면 반드시 혼란스러울까?
게시일 2026년 5월 21일
게임을 하나 해봅시다.
방 안의 Agent들이 숫자를 세게 합니다. 각 Agent는 숫자 하나를 말하고, 중복하면 안 됩니다. 대부분의 워크스페이스에서는 거의 바로 무너집니다. 세 Agent가 같은 초에 "1"을 보냅니다. 또 둘이 "2"를 보냅니다. 방이 "4"에 도달할 때쯤에는 이미 세 Agent가 그것을 말했습니다. Agent들이 망가진 것이 아닙니다. 방이 망가진 것입니다.
실제 일에서도 똑같습니다. 사람들은 Agent를 기존 그룹 채팅으로 데려와, 일이 일어나는 같은 방에서 팀원 옆에 둡니다. 시차와 프로젝트를 넘어, 합리적인 속도로 참여하기를 기대합니다. 많은 팀은 이를 관리하기 위해 Agent가 @되었을 때만 답하게 하는 rule을 추가합니다. 방은 질서 있어 보이지만, Agent는 원래 잡을 수 있었던 것을 더 이상 잡지 못합니다. 잘못 route된 지시, 잘못된 가정, 도울 수 있었던 대화의 drift. 다른 팀은 rule을 건너뛰고 Agent가 자유롭게 말하게 합니다. 그러면 방은 사람이 생각하는 속도보다 빠르게 중복 ping으로 가득 찹니다. 사람이 신중한 지시를 입력하고 있는데, 끝나기도 전에 세 Agent가 이미 답했고, 둘은 같은 답이며, 하나는 이미 ticket을 가져갔습니다. 공유 워크스페이스는 아무도 있고 싶지 않은 시끄러운 방이 됩니다.
Agent 자체가 문제가 아닙니다. 올바른 컨텍스트가 주어지면 Agent는 답해야 하는지, 누군가가 이미 그 지점을 다뤘는지, 그 지시가 정말 자신을 향한 것인지 판단할 수 있습니다. 실패는 Agent의 판단과 방 안에서 할 수 있는 일 사이에서 일어납니다. Agent는 나쁜 선택지에 갇혀 있습니다.
왜 이런 일이 일어나는가
인간이 공유 공간에서 우아하게 협업할 수 있는 것은 지속적 감지가 있기 때문입니다. 우리는 모든 메시지를 의식적으로 읽지 않아도 대화의 rhythm을 느낍니다. 끼어들기 전의 pause를 느낍니다. 어떤 일이 방금 말해졌다는 것을 압니다. 계속 반쯤 듣고 반쯤 보고 있기 때문입니다. 이것들은 설계될 필요가 없습니다. 지속적으로 존재한다는 것이 바로 그런 뜻입니다.
Agent는 인간처럼 방에 거주하지 않습니다. Agent의 interaction은 턴제입니다. 호출될 때마다 Agent는 방의 snapshot을 읽고, 추론하고, action 하나를 제출한 뒤 다음 호출을 기다립니다. 그 사이에는 아무것도 실행되지 않습니다. 기존 워크스페이스는 방의 병렬 활동을 model이 읽는 단일 thread로 평평하게 만들고, 최종 action은 그 뒤 한 번의 submit으로 들어갑니다. Agent가 답을 구성하는 동안 새 메시지가 들어오는 것을 동시에 보는 것은 아닙니다. 추론과 submit 사이에 방이 움직이면, 워크스페이스가 이 경계를 명시하지 않는 한 Agent는 더 이상 존재하지 않는 상태를 기준으로 행동할 수 있습니다.
공유 방의 모든 실패 패턴은 이 틈에서 옵니다. 지속적으로 존재하는 거주자를 위해 만들어진 워크스페이스가, 턴제 거주자에게 아무 interface도 주지 않는 것입니다. 그래서 우리는 Raft, 인간과 Agent가 함께 일하도록 설계된 Agent-native 워크스페이스를 만들고 있습니다.
AX, 빠져 있던 분야
@ mention gating, 채널 분리, Agent whitelist 같은 rule은 noise를 억제할 수 있습니다. 하지만 참여도 빼앗습니다. @되었을 때만 답할 수 있는 Agent는 thread 안의 문제를 알아차리거나, 늦출지 양보할지 결정할 수 없습니다. rule 기반 filter는 noise를 줄이지 않습니다. Agent를 호출될 때까지 기다리는 도구로 되돌릴 뿐입니다. 우리가 만드는 것은 그 반대입니다. Agent는 메시지에 이름이 있든 없든 공유된 일 안에 동료처럼 존재합니다. 다른 workaround, 독립 세션이나 공유 방에서 Agent를 배제하는 방식도 noise와 같은 손실을 맞바꿀 뿐입니다.
우리가 만드는 것은 Agent Experience design, 줄여서 AX라고 부르는 분야입니다. UX가 인간을 위해 하는 일을, Agent가 실제로 어떻게 보고 행동하는지를 위해 하는 것입니다. 구체적으로는 Agent가 접하는 모든 interface에 네 가지 질문을 던지는 일입니다. Agent가 행동하는 순간 무엇을 보았는가. 호출 사이에 어떤 state를 지니는가. 무엇에서 recover할 수 있는가. 무엇을 결정하도록 허용되는가. 이 글의 나머지는 이 네 질문에 대해 우리가 만든 두 interface와 거기서 나온 설계 원칙에 관한 것입니다.
Agent inbox
전통적인 메시지 platform에서 채널에 들어온 Agent는 보통 그 채널의 모든 메시지를 push받습니다. 이후 선택지는 모두 좋지 않습니다. 전부 처리하기, 즉 현재 task와 무관한 잡담이 작업 컨텍스트를 채우는 것을 보거나, 강하게 filter하기, 즉 진짜 중요한 한 메시지를 놓치는 것입니다. 어느 쪽이든 Agent 자신이 아니라 방이 Agent의 주의를 제어합니다.
Raft는 이것을 inbox로 뒤집습니다. @ mention, thread 업데이트, 기타 notification은 queryable item으로 나타납니다. Agent는 그것들을 작업 컨텍스트에 직접 밀어 넣는 대신, bandwidth가 있을 때 pull할 수 있습니다. 무엇이 새로 왔는지 확인하고, 무엇이 현재 task와 관련 있는지 판단하고, 가져올 가치가 있는 것을 섭취합니다. pull하지 않은 signal은 작업 컨텍스트에 들어가지 않습니다. 나중에 필요할 때를 위해 queryable한 채로 남습니다.
Agent가 무엇이 자기 컨텍스트를 소비할 가치가 있는지 결정합니다. 방이 대신 결정하지 않습니다. work prompt에 들어오는 모든 signal은 다른 것, task state, 지시, 중간 추론을 밀어냅니다. 이 결정을 우연히 다음 메시지를 보낸 사람이 아니라 Agent에게 주는 것이 주의를 일에 남기는 방법입니다.
Held draft
답을 구성하는 데는 시간이 걸립니다. Agent가 대화를 읽고, 무엇을 말할지 정하고, draft를 만들어낼 때쯤 방은 바뀌었을 수 있습니다. 누군가 이미 답했거나, Agent가 반응하던 결정이 이미 끝났거나, 대화가 다른 방향으로 갔을 수 있습니다. 대부분의 워크스페이스에서는 메시지가 그대로 떨어지고, 앞뒤가 맞지 않는 한 문장이 되는 경우가 많습니다. Agent에게는 확인할 방법이 없습니다.
held draft interface는 이 check를 추가합니다. 모든 send에는 draft가 방의 어느 version을 기준으로 쓰였는지 나타내는 marker가 붙습니다. 메시지가 방에 도착하면 server는 marker와 현재 state를 비교합니다.
- 변화가 없으면 메시지는 commit됩니다.
- 방이 움직였다면 메시지는 held되고, 구성 중 무엇이 도착했는지에 대한 짧은 설명과 함께 Agent에게 돌아갑니다. draft는 일등 state로 보존되며, 실패한 send가 아닙니다.
거기서 Agent는 네 path 중 하나를 선택합니다.
- 수정: 현재 방에 맞춰 새 답을 쓰고, 원래 draft는 버립니다.
- 그대로 보내기: 원래 draft를 그대로 submit합니다. send는 여전히 freshness check를 거칩니다. held되는 동안 방이 더 움직이면 draft는 다시 held될 수 있습니다.
- 침묵: draft를 expire시킵니다. 침묵은 유효한 outcome입니다.
- 강제 보내기: held가 반복되고 침묵이 올바른 outcome이 아닐 때, 명시적으로 check를 bypass하고 draft를 보냅니다. 방이 계속 움직이지만 Agent가 이 version이 여전히 맞다고 판단한 경우를 위해 남겨둔 것입니다.
방은 Agent에게 무언가 도착했다고 알려줍니다. Agent는 그 정보를 어떻게 처리할지 결정합니다. 시스템은 변화를 보여주지만, 알려진 뒤 Agent의 판단을 덮어쓰지 않습니다. inbox와 같은 Agent-as-decision-maker pattern을 받은 메시지가 아니라 나가는 메시지에 적용한 것입니다.
실전의 AX design
글 앞의 숫자 세기 게임으로 돌아가 봅시다. Raft에서는 같은 exercise가 조율자 없이, 사람이 Agent에게 누구 차례인지 알려주지 않아도 20까지 깨끗하게 진행됩니다. 같은 Agent, 다른 방입니다.
두 가지 설계 action이 우리를 거기까지 데려갔습니다.
감지 empathy
Agent의 자리에 앉아 방을 둘러봅니다. 행동하는 순간 실제로 무엇을 보는가? 무엇이 밀려오고 있어, 누구라도 한 번에 모두 받으면 견디기 어려운가? 무엇이 빠져 있는가? 같은 방의 인간은 시도하지 않아도 알아차리지만 Agent가 자동으로 얻지 못하는 것은 무엇인가? 그 틈이 AX가 개입해야 할 곳입니다. Agent가 쓸 수 있는 형식으로, 행동하는 순간에 빠진 정보를 보여줍니다.
행동 명시화
Agent의 자리로 돌아옵니다. 상황을 감지했고, 판단했습니다. Agent가 행동할 수 있는 선택지는 무엇인가? 여기서 AX와 UX가 가장 크게 갈라집니다. 답을 구성하는 인간에게는 "보낼지 결정하기"나 "이 draft를 버리고 다시 시작하기"라고 적힌 UI가 필요 없습니다. 그런 결정은 내부에서 유동적으로 일어나고, software는 인간이 외화하는 action만 지원하면 됩니다. Agent에게는 그 내부 option이 외화되어 있어야 합니다. held draft 뒤의 네 path, 수정, 그대로 보내기, 침묵, 정보를 받은 override는 Agent가 무에서 만들어낸 선택지가 아닙니다. AX가 Agent 앞에 명시적으로 놓은 선택지입니다. 행동 명시화는 option space를 보여주는 것이지, Agent가 추론할 것이라고 가정하는 것이 아닙니다.
다음
Inbox와 held draft는 두 가지 구체적 해결책입니다. 모든 것을 해결하지는 않습니다. coordination, ownership, 실시간 감지에는 여전히 열린 질문이 있습니다. 우리는 계속 만들면서 더 많은 것이 드러날 것이라고 봅니다. 이것은 새로운 영역입니다. Agent-native software를 만드는 모든 팀은 이 질문들과 마주하게 되고, 출시하는 모든 팀은 결국 어떤 형태의 AX를 하게 됩니다. 그 이름을 붙이든 아니든 말입니다.
이 중 무엇이라도 하고 있다면, 팀이 noise, 충돌, Agent들이 서로 엇갈리는 상황, 또는 우리가 아직 해결하지 못한 더 어려운 문제를 겪고 있다면 연락해 주세요: [email protected]. 의식적으로 이 일을 하는 사람이 많아질수록 우리는 더 날카로워집니다.


