약 7분 읽기
고객사의 RPA 운영 담당자가 Dify로 챗봇을 만들겠다고 했다. 채팅창에 과제명과 인수만 자연어로 적으면, 사내에 설치된 UiPath Orchestrator가 그 프로세스를 실행하는 구조다. 담당자는 개발 경험 없이 직접 공부해서 Dify를 구성할 생각이었다. 처음 요청은 간단했다. “Swagger 주소만 알려주면 나머지는 해보겠다.”
나는 이 프로젝트에서 코디네이터였다. 직접 만들지는 않지만, 담당자가 헤매지 않도록 넘겨줄 정보를 정리하는 역할이다. 정리하다 보니 Swagger 주소보다 먼저 확인해야 할 게 세 가지 있었다. 이 글은 그 세 가지와, 실제로 넘긴 정보를 정리한 기록이다.

Dify 서버는 어디에 있는가
이 고객사의 Orchestrator는 온프레미스다. IIS 위에 standalone으로 설치돼 있고, 본사 내부망에서만 접근할 수 있다. 외부 인터넷에서는 Orchestrator 주소 자체를 찾을 수 없다.
그러면 Dify가 어디서 돌고 있느냐에 따라 가능 여부가 갈린다.
- 클라우드형 Dify(dify.ai 같은 외부 서비스): 불가능하다. 외부 서버에서 내부망 주소로 요청을 보낼 길이 없다.
- 본사 내부망 서버에 설치한 Dify: 가능하다.
- VPN으로 내부망에 붙을 수 있는 서버의 Dify: 가능하다.
그래서 담당자에게 가장 먼저 물은 건 Swagger가 아니라 “Dify 서버가 어디 있느냐”였다. 클라우드형으로 시작했다면, API를 아무리 잘 짜도 연결되지 않는다. 그 경우엔 설계부터 다시 해야 한다. 개발 경험이 없는 사람이 혼자 공부하다 가장 오래 막히는 지점이 이런 곳이다. 에러 메시지는 “연결할 수 없음” 정도로만 나오고, 원인이 네트워크라는 힌트는 주지 않는다.
admin 계정을 넘기면 안 되는 이유
정리하다 보니 처음 넘기려던 계정이 admin이었다. Orchestrator의 최고 관리자 계정이다. 이걸 Dify에 넣으면, 챗봇이 프로세스를 실행하는 것뿐 아니라 사용자를 지우고, 로봇 설정을 바꾸고, 패키지를 교체할 수 있는 권한까지 갖게 된다. 챗봇 설정 화면에 그 비밀번호가 저장되는 것도 문제다.
그래서 이렇게 바꾸자고 했다.
- Orchestrator 관리자에게 Dify 전용 로컬 계정을 하나 만들어 달라고 요청한다.
- 권한은 잡 실행에 필요한 최소한만 준다. 로봇(Robots)과 잡(Jobs) 관련 권한 정도다.
- Dify 담당자에게는 그 서비스 계정 정보만 전달한다.
이렇게 해두면 나중에 챗봇이 잘못된 요청을 보내더라도 피해 범위가 잡 실행으로 한정된다. 계정을 따로 두면 로그에서 “챗봇이 실행한 잡”을 구분하기도 쉬워진다.
Swagger로 찾아야 할 API는 세 개뿐이다
Orchestrator 주소 뒤에 /swagger를 붙이면 사용할 수 있는 API 목록과 사용법이 나온다. 그런데 처음 열어보면 API가 수백 개라 어디서 시작할지 모른다. 챗봇으로 잡 하나를 실행하는 데 필요한 건 세 개다.
# 1) 온프레미스 Orchestrator 인증 → Bearer 토큰
POST {오케스트레이터}/api/Account/Authenticate
{ "tenancyName": "{테넌트}", "usernameOrEmailAddress": "{서비스 계정}", "password": "{비밀번호}" }
# 2) 실행할 프로세스의 ReleaseKey 찾기
GET {오케스트레이터}/odata/Releases?$filter=Name eq '{프로세스명}'
X-UIPATH-OrganizationUnitId: {폴더 ID}
# 3) 잡 실행 — 인수는 JSON "문자열"로 넣는다
POST {오케스트레이터}/odata/Jobs/UiPath.Server.Configuration.OData.StartJobs
X-UIPATH-OrganizationUnitId: {폴더 ID}
{ "startInfo": {
"ReleaseKey": "{ReleaseKey}",
"Strategy": "ModernJobsCount",
"JobsCount": 1,
"InputArguments": "{\"in_기준일\":\"2026-05-06\"}"
} }
- 인증: 온프레미스에서는
/api/Account/Authenticate에 테넌트명, 계정, 비밀번호를 보내 Bearer 토큰을 받는다. - ReleaseKey 찾기: 사람이 아는 건 “과제명”인데, 실행 API는 ReleaseKey를 요구한다.
/odata/Releases를 프로세스 이름으로 필터해서 키를 얻는다. - 잡 실행:
StartJobs에 ReleaseKey와 인수를 넣어 보낸다.
여기서 초보자가 자주 걸리는 지점이 두 개 있다. 하나는 폴더다. 최근 Orchestrator는 프로세스를 폴더 단위로 관리해서, 요청 헤더 X-UIPATH-OrganizationUnitId에 폴더 ID를 넣지 않으면 프로세스를 못 찾는다. 다른 하나는 인수 형식이다. InputArguments는 JSON 객체가 아니라 JSON을 문자열로 한 번 더 감싼 값이어야 한다. 자연어에서 뽑은 인수를 그대로 넣으면 형식 오류가 난다.
챗봇을 만들기 전에 연결부터 시험한다
담당자에게 꼭 해보라고 한 게 하나 있다. 챗봇 화면을 만들기 전에, Dify가 설치된 서버에서 Orchestrator로 요청이 실제로 닿는지부터 확인하는 것이다. 그 서버의 터미널에서 인증 API에 curl로 요청을 한 번 보내면 된다.
- 응답이 아예 없거나 주소를 찾지 못하면: 네트워크 문제다. Dify 위치나 방화벽부터 본다.
- 인증서 오류가 나면: 내부망 인증서를 그 서버가 신뢰하지 못하는 경우다.
- 401이 오면: 연결은 됐고 계정 정보가 틀린 것이다.
- 토큰이 오면: 연결과 인증이 모두 된 것이다. 이제 챗봇을 만들면 된다.
이 한 줄로 문제를 네트워크, 인증서, 계정 세 갈래로 나눌 수 있다. 챗봇까지 다 만든 뒤에 “실행이 안 된다”를 만나면, 원인이 프롬프트인지 API 호출인지 네트워크인지 가늠하기 어렵다.
실제로 넘긴 정보
담당자에게 넘기려고 정리한 목록은 아래와 같다.
- Orchestrator 주소와 Swagger 주소
- 테넌트명
- 계정: admin 대신 Dify 전용 서비스 계정을 만들어 별도 경로로 전달
- 네트워크 조건: 본사 내부망에서만 접근 가능, 클라우드형 Dify는 연결 불가
목록은 짧지만, 각 줄 뒤에는 “왜 이게 필요한가”를 한 문장씩 붙였다. 개발 경험이 없는 사람에게는 무엇을 넣는지만큼 왜 그걸 넣는지가 중요하다. 그래야 다음에 막혔을 때 스스로 원인을 짐작할 수 있다.
그다음에 난 에러는 Dify 문제가 아니었다
연결 구성이 끝난 뒤 담당자가 에러 화면을 보내왔다. 화면을 보니 원인은 Dify 설정이 아니라, Dify에 연결된 OpenAI API 키의 쿼터와 결제 한도였다. 키 자체가 틀린 게 아니라, 그 키가 속한 프로젝트에 쓸 수 있는 크레딧이 없거나 결제 한도에 막혀 있는 상태였다.
이런 에러는 Dify 화면에서 보면 Dify가 고장 난 것처럼 보인다. 확인 순서는 이렇다. 먼저 API 키가 결제가 연결된 프로젝트의 키인지 본다. 그다음 그 프로젝트의 사용 한도를 본다. 당장 해결이 안 되면 Dify의 모델 공급자를 다른 곳으로 바꾸는 방법이 있다. 이때는 Anthropic 모델 공급자를 설정하는 경로를 안내했다.
돌아보면 이 일에서 코드는 거의 쓰지 않았다. 한 일은 질문의 순서를 정한 것이다. 어디서 돌아가는가, 어떤 권한으로 돌아가는가, 무엇을 호출하는가. 이 세 질문에 먼저 답하면 Swagger 문서는 그다음에 열어도 늦지 않다.