Telegram·Discord 봇
이미지와 영상을 만들고, 이미지를 움직이는 영상으로 바꾸고, 직접 정의한 캐릭터와 대화하는 나만의 비공개 봇을 운영하세요. SpicyAPI 잔액으로 결제하며 결제 전에 지출 한도를 검사합니다.
SpicyAPI 봇은 직접 실행하는 작은 프로그램입니다. Telegram(원하면 Discord도)에 연결되어, 내가 허용한 사람들이 이미지를 생성하고, 영상을 만들고, 이미지를 영상으로 바꾸고, 내가 정의한 캐릭터와 대화할 수 있게 해 줍니다. 모든 비용은 내 SpicyAPI 잔액에서 결제되며, 모든 요청은 결제 전에 가격이 먼저 산정됩니다.
봇은 무료 오픈 소스(MIT)이며 github.com/spicyapi-ai/spicyapi-bot에서 받을 수 있습니다. 기본값은 비공개입니다. 다른 사람이나 그룹을 허용하기 전까지는 나만 쓸 수 있습니다.
한눈에 보기
- 콘솔에서 봇 전용 API 키를 만들고 일일 지출 한도를 설정하세요.
- Telegram에서 @BotFather에게 메시지를 보내
/newbot을 전송하고 토큰을 복사하세요. - 저장소를 클론하고
.env.example을.env로 복사한 뒤SPICY_API_KEY,TELEGRAM_BOT_TOKEN,OWNER_ID를 채우고docker compose up -d --build를 실행하세요. - Telegram에서 내 봇을 열고
/start를 보낸 뒤 규칙에 동의하고/pic a cozy cabin in the snow를 시도해 보세요.
봇이 하는 일
- 이미지:
/pic a lighthouse at dusk - 영상:
/vid waves rolling onto a beach at sunset - Animate: 봇이 만든 이미지 아래의 Animate를 누르거나, 그 이미지에
/animate <how it should move>로 답장하세요. - 캐릭터 채팅: 비공개 채팅에서 입력하거나
/talk를 쓰세요. 답변은 하나의 메시지로 스트리밍됩니다. - 지출 보호: 요청마다 먼저 가격이 산정되고(견적은 무료), 비싼 요청은 Confirm을 눌러야 하며, 개인별 한도와 봇 전체의 일일 한도가 적용됩니다.
- 기본값은 비공개: 허용하기 전에는 다른 사람이 쓸 수 없습니다.
SpicyAPI 카탈로그에는 자체 콘텐츠 필터를 두지 않는 검열 없는 모델이 포함되어 있고, 봇은 내가 고른 어떤 모델과도 작동합니다. 생성하는 모든 것에는 법률과 SpicyAPI의 콘텐츠 정책이 여전히 적용됩니다. 정책을 보세요.
명령
| 명령 | 하는 일 |
|---|---|
/pic <prompt> | 이미지를 생성합니다 |
/vid <prompt> | 텍스트로 영상을 생성합니다 |
/animate <motion> | 이미지에 답장해 영상으로 바꿉니다. 봇이 만든 이미지는 항상 되고, 내 사진은 운영자가 ALLOW_PHOTO_UPLOADS=true로 설정한 경우에만 됩니다 |
| Animate 버튼 | 생성된 모든 이미지 아래에 있으며, 이미지의 프롬프트를 재사용해 움직이는 영상으로 만듭니다 |
/talk <message> | 현재 캐릭터와 대화합니다(비공개 채팅에서는 그냥 입력하면 됩니다) |
/persona | 캐릭터를 선택합니다 |
/newchat | 대화를 잊고 처음부터 다시 시작합니다 |
/models | 이미지, 영상, animate, 채팅 모델을 선택합니다 |
/spend | 오늘 쓴 금액을 보여 줍니다. 소유자는 봇 전체와 계정 잔액도 봅니다 |
/report <text> | 운영자에게 신고를 보냅니다 |
/help | 위 내용을 모두 요약해 보여 줍니다 |
다른 인기 봇들이 쓰는 /image, /video, /chat은 의도적으로 피한 이름이므로 이 봇은 그런 봇들과 한 그룹에서 함께 쓸 수 있습니다. Telegram 그룹에서는 봇의 채팅 메시지에 답장하면 캐릭터와 계속 대화할 수 있습니다.
시작하기 전에
- 항상 켜져 있는 컴퓨터나 서버와 설치된 Docker. (또는 Railway 계정, 아래 참고.)
- 잔액이 있는 SpicyAPI 계정. 계정 설정과 과금을 보세요.
- BotFather로 봇을 만들기 위한 Telegram 계정.
Docker Compose로 배포하기
봇 전용 키 만들기
콘솔에서 이 봇 전용 새 API 키를 만드세요. 이 키에 일일 지출 한도를 설정하고, 원한다면 허용할 모델 목록도 지정하세요.
봇에도 자체 한도가 있지만, 키의 한도는 SpicyAPI가 직접 적용하므로 봇 설정이 잘못되거나 데이터를 잃어도 유지됩니다. 새 키는 설정하지 않는 한 한도가 없습니다. 인증을 보세요.
Telegram 봇 만들기
@BotFather를 열고 /newbot을 보낸 뒤 이름과 사용자 이름을 정하고, 받은 토큰을 복사하세요. 토큰은 123456789:AA...처럼 생겼습니다.
설정하기
git clone https://github.com/spicyapi-ai/spicyapi-bot.git
cd spicyapi-bot
cp .env.example .env.env를 열어 필수 세 줄을 채우세요.
SPICY_API_KEY=sk-spicy-...
TELEGRAM_BOT_TOKEN=123456789:AA...
OWNER_ID=your-telegram-user-id나머지 줄은 모두 안전한 기본값이 있습니다. .env.example에 각 설정이 설명되어 있습니다.
Telegram 사용자 ID 찾기(모르는 경우)
일단 OWNER_ID=0으로 두고 다음 단계를 마치세요. 그런 다음 봇에게 아무 메시지나 보내면 내 ID로 답합니다. 그 숫자를 OWNER_ID에 넣고 다시 시작하세요.
docker compose up -d시작하기
docker compose up -d --build
docker compose logs -f준비가 끝나면 로그에 Telegram bot @yourbot is running이 표시됩니다.
써 보기
Telegram에서 내 봇을 열고 /start를 보낸 뒤 규칙에 한 번 동의하고 /pic a cozy cabin in the snow를 보내세요. 기본 이미지 모델은 이미지 한 장에 약 $0.01입니다.
나중에 업데이트하려면 git pull && docker compose up -d --build를 실행하세요.
Railway에 배포하기
Railway에서는 서버 없이도 봇을 실행할 수 있습니다. 원클릭 템플릿은 없으며, 내 저장소 사본에서 배포합니다.
저장소 포크하기
github.com/spicyapi-ai/spicyapi-bot을 내 GitHub 계정으로 포크하세요.
프로젝트 만들기
Railway에서 New Project > Deploy from GitHub repo를 선택하고 포크한 저장소를 고르세요. Railway가 Dockerfile을 찾아 빌드합니다.
변수 추가하기
서비스의 Variables 탭을 열고 SPICY_API_KEY, TELEGRAM_BOT_TOKEN, OWNER_ID와 .env.example에 있는 다른 설정을 추가하세요.
볼륨 연결하기
서비스를 마우스 오른쪽 버튼으로 클릭하고 Attach volume을 선택한 뒤 마운트 경로를 /data로 지정하세요. 볼륨이 없으면 재배포할 때마다 오늘의 지출과 모두의 설정을 잊어버립니다.
배포하기
배포하고 로그에서 Telegram bot @yourbot is running을 확인하세요.
서비스는 레플리카 하나로 유지하세요. 같은 Telegram 토큰을 폴링하는 사본이 둘이면 업데이트를 두고 충돌합니다. 봇에는 공개 도메인도, 열린 포트도 필요하지 않습니다.
Discord 추가하기(선택)
애플리케이션 만들기
Discord Developer Portal에서 애플리케이션을 만들고 Bot을 연 뒤 토큰을 재설정해 복사하고, Public Bot을 꺼서 나만 서버에 추가할 수 있게 하세요. 권한이 필요한 인텐트(privileged intents)는 필요하지 않습니다.
서버에 초대하기
OAuth2 > URL Generator에서 스코프 bot과 applications.commands를 체크하고, 권한은 Send Messages, Attach Files, Embed Links, Read Message History를 체크하세요. 생성된 링크를 열어 봇을 서버에 추가하세요.
설정하기
.env에서 다음을 설정하세요.
DISCORD_TOKEN은 봇 토큰.DISCORD_GUILD_ID는 내 서버 ID. 명령이 짧은 전역 배포를 기다리지 않고 바로 나타나게 하려면 설정하세요.OWNER_ID에는 내 Discord 사용자 ID를 포함하세요. 예:OWNER_ID=tg:123,dc:456.tg:와dc:접두사는 ID를 한 플랫폼에 고정합니다.ALLOWED_CHAT_IDS는 봇이 응답할 채널 또는 서버 ID.
ID를 찾으려면 개발자 모드(User Settings > Advanced)를 켠 뒤 사용자, 채널, 서버를 마우스 오른쪽 버튼으로 클릭하고 Copy ID를 선택하세요. 봇을 다시 시작하세요.
채널을 연령 제한으로 설정하기
이미지와 영상은 연령 제한 채널에서만 작동합니다. Edit Channel > Overview > Age-Restricted Channel에서 설정하세요. /pic과 /vid 명령은 연령 제한으로 등록되어 있어 Discord가 그곳에서만 보여 줍니다.
채팅(/talk 또는 봇 멘션)은 DISCORD_CHAT_REQUIRES_NSFW=true로 설정하지 않는 한 허용된 모든 채널에서 작동합니다. 이 값을 설정하면 채팅도 연령 제한 채널로 제한됩니다.
Discord는 연령 제한 명령이 있는 앱을 App Directory에 올리지 못하게 하므로 봇은 비공개로 유지하세요. .env.example에는 DISCORD_MEDIA_IN_DMS도 있으며 기본값은 false입니다. 이 경우 이미지와 영상은 연령 제한 서버 채널에서만 작동하고 다이렉트 메시지에서는 작동하지 않습니다.
누가 쓸 수 있나요
| 설정 | 기본값 | 효과 |
|---|---|---|
OWNER_ID | 필수 | 나 자신입니다. 항상 허용되고, 개인별 일일 한도의 적용을 받지 않으며, 계정 잔액을 볼 수 있는 유일한 사람입니다. 여러 ID는 쉼표로 구분하세요. |
ALLOWED_USER_IDS | 비어 있음 | 비공개 채팅에서 허용되는 다른 사람들입니다. 비어 있으면 나만 쓸 수 있습니다. |
ALLOWED_CHAT_IDS | 비어 있음 | 봇이 응답하는 그룹(Telegram) 또는 채널과 서버(Discord)입니다. 비어 있으면 그룹은 하나도 허용되지 않습니다. |
REQUIRE_CONSENT | true | 모든 사람이 18세 이상이며 콘텐츠 규칙을 따르겠다고 한 번 확인합니다. |
봇을 발견한 낯선 사람에게는 비공개 봇이라는 안내와 함께, 나에게 보낼 수 있도록 그 사람의 사용자 ID가 전달됩니다. 그룹은 ALLOWED_CHAT_IDS에 올리기 전까지 무시되며, 그룹을 올리면 그 그룹의 모든 구성원이 일일 한도 안에서 봇을 쓸 수 있습니다. Telegram 그룹 ID는 음수입니다. 예: -1001234567890.
ALLOWED_USER_IDS=*는 설정하지 마세요
ALLOWED_USER_IDS=*는 봇을 공개로 만들어, 봇을 발견한 누구나 내 잔액을 쓸 수 있게 합니다. 의도한 경우에만 쓰세요.
이 봇은 내가 운영하며, 누구에게 쓰게 할지에 대한 책임도 나에게 있습니다. SpicyAPI의 약관이 적용되며, SpicyAPI가 서비스하지 않는 지역에 관한 내용도 포함됩니다.
지출이 처리되는 방식
- 가격이 먼저. 이미지나 영상은 무엇이든 실행하기 전에 SpicyAPI가 견적을 냅니다. 견적은 무료입니다.
- 절대 상한. 요청 비용이
MAX_COST_PER_REQUEST_USD(기본값 $1)를 넘을 수 있으면 거부됩니다. 요금은 부과되지 않습니다. - 확인. 비용이
CONFIRM_ABOVE_USD(기본값 $0.10)를 넘을 수 있으면 봇이 가격과 함께 Confirm, Cancel 버튼을 보여 줍니다. 요청한 본인만 확인할 수 있습니다. - 일일 한도. 한 사람은 UTC 하루에
USER_DAILY_BUDGET_USD(기본값 $1)까지, 봇 전체는DAILY_BUDGET_USD(기본값 $5)까지 쓸 수 있습니다. 아직 진행 중인 생성은 끝날 때까지 쓴 금액으로 계산되므로, 여러 요청을 동시에 보내도 한도를 우회할 수 없습니다. 소유자는 봇 전체 한도만 적용받습니다. - 이중 결제 없음. 모든 요청에는 채팅 메시지나 버튼 탭에서 파생된 멱등성 키가 붙으므로, 중복된 Telegram 업데이트나 더블 탭이 오면 이미 존재하는 작업을 반환합니다.
- 결과. 진행 상황은 몇 초마다 메시지 하나를 수정하는 방식으로 표시됩니다. 결과에는 실제 청구 금액과 작업 ID가 표시되며, 작업 ID는 콘솔의 Logs에서 조회할 수 있습니다.
접수된 생성은 취소할 수 없습니다. 성공한 실행은 과금되며 일반적인 실패는 보류 금액을 해제합니다. 일부 콘텐츠 거부는 해당 모델 페이지에 과금한다고 명시된 경우에만 청구됩니다. 과금을 보세요.
한도를 건 키 쓰기
봇은 DATA_DIR/state.json에 자체 장부를 둡니다. 이 파일을 잃으면 봇은 오늘 쓴 금액을 잊어버립니다. 콘솔에서 API 키에 건 한도는 SpicyAPI가 직접 적용하므로 절대 사라지지 않는 한도입니다. 봇 전용 키를 따로 만들어 일일 지출 한도를 설정하고, 원하면 허용할 모델만 지정하세요. 한도에 도달하면 봇이 키가 지출 한도에 도달했다고 알려 줍니다.
그 밖의 유용한 설정입니다.
| 설정 | 기본값 | 하는 일 |
|---|---|---|
MAX_CONCURRENT_TASKS_PER_USER | 2 | 한 사람이 동시에 진행할 수 있는 이미지와 영상의 수 |
VIDEO_SECONDS / VIDEO_RESOLUTION | 5 / 480p | 영상의 길이와 크기. 각 모델이 허용하는 값에 맞춰집니다. 짧고 낮을수록 저렴합니다 |
ALLOWED_MODELS | 비어 있음 | /models 메뉴를 제한합니다. 정확한 ID나 *로 끝나는 접두사를 씁니다. 예: alibaba/* |
모델과 가격
각 사용자는 /models로 자기 모델을 바꿀 수 있습니다. 기본값은 운영자가 정합니다.
| 변수 | 기본값 | 작성 시점의 비용 |
|---|---|---|
DEFAULT_IMAGE_MODEL | Z-Image Turbo, 텍스트로 이미지 | 이미지당 약 $0.01 |
DEFAULT_VIDEO_MODEL | MiniMax H3, 텍스트로 영상 | 768p 기준 초당 약 $0.037 |
DEFAULT_ANIMATE_MODEL | MiniMax H3, 이미지로 영상 | 768p 기준 초당 약 $0.037 |
DEFAULT_CHAT_MODEL | DeepSeek V4.1 Flash | 카탈로그의 모든 채팅 모델 |
정확한 모델 ID는 .env.example에 있습니다. 바꾸려면 실시간 카탈로그(GET /api/v1/models)에서 다른 ID를 복사하세요(아래 캐릭터 예시에서 MODEL_ID_FROM_CATALOG는 그런 ID가 들어갈 자리를 나타냅니다). 가격은 공개 카탈로그 기준이며 바뀔 수 있고, 봇은 항상 실시간 견적을 보여 줍니다. 모델은 spicyapi.ai/models에서 둘러보거나 모델을 보세요. 롤플레이용 채팅 모델은 롤플레이 리더보드가 고르는 데 도움이 됩니다.
캐릭터
캐릭터는 JSON 파일(CHARACTERS_FILE, 기본값 characters/default.json, 예시 캐릭터 두 개 포함)에 정의합니다.
{
"characters": [
{
"id": "mira",
"name": "Mira",
"system": "You are Mira, ... Never speak or act for {{user}}.",
"greeting": "Welcome aboard, {{user}}!",
"model": "MODEL_ID_FROM_CATALOG"
}
]
}system은 캐릭터에 대한 지시문입니다.greeting(선택)은 캐릭터의 첫 대사입니다.model(선택)은 이 캐릭터에 쓸 채팅 모델을 고정합니다.{{char}}와{{user}}는 캐릭터의 이름과 사용자의 이름(first name)으로 치환됩니다.- 항목은 Character Card V2 JSON일 수도 있습니다. 대부분의 캐릭터 사이트와 SillyTavern이 내보내는 형식입니다. 설명, 성격, 시나리오, 예시 대화, 첫 메시지가 사용됩니다.
Docker에서는 내 파일을 마운트하고 설정이 그 파일을 가리키게 하세요. docker-compose.yml에서:
volumes:
- ./my-characters.json:/app/characters/custom.json:ro그리고 .env에서:
CHARACTERS_FILE=characters/custom.json봇은 대화마다 HISTORY_TURNS번의 주고받기(기본값 20)를 기억하고, 답변을 CHAT_MAX_TOKENS 토큰(기본값 2048)으로 제한합니다. 추론 모델은 생각하는 데 쓴 토큰도 이 한도에 포함하므로, 값이 너무 작으면 답변할 여유가 남지 않을 수 있습니다. 캐릭터를 쓰는 방법은 채팅 레시피를 더 보세요.
사진 업로드는 기본적으로 꺼져 있습니다
기본적으로는 봇이 생성한 이미지만 움직이는 영상으로 만들 수 있습니다. 실제 사람의 사진을 영상으로 바꾸는 것이 이런 봇이 악용되는 대표적인 경로이며, 사진 속 사람은 내 영상에 등장하기로 동의한 적이 없습니다.
ALLOW_PHOTO_UPLOADS=true로 설정하면 내가 허용한 누구나 자기가 보낸 사진을 영상으로 만들 수 있습니다. 믿을 수 있는 사람에게만, 그리고 동의한 성인의 사진에만 쓰도록 켜세요. 켜져 있으면 업로드된 이미지는 봇이 내려받아 SpicyAPI에 저장합니다. Telegram 파일 링크에는 봇 토큰이 들어 있으므로 절대 전달하지 않습니다.
개인정보: 무엇이 어디에 저장되나요
| 대상 | 저장 위치 | 보관 기간 |
|---|---|---|
| 일일 지출 합계, 사람별 모델과 캐릭터 선택, 규칙에 동의한 사람 | DATA_DIR의 state.json(Docker에서는 볼륨) | 삭제할 때까지 |
| 채팅 기록 | 메모리에만 | 재시작, 하루 동안 활동 없음, 또는 /newchat 시 사라짐 |
| 봇 로그 | 내 컴퓨터 | 작업 ID와 금액만 남고, 프롬프트나 미디어는 절대 남기지 않음 |
| 프롬프트와 결과 | SpicyAPI | 계정의 보관 기간. 보관 기간을 보세요 |
계정 기본값보다 일찍 결과와 프롬프트를 삭제하도록 SpicyAPI에 요청하려면 RETENTION_SECONDS를 설정하세요.
그룹에서는 결과가 스포일러 뒤에 숨겨집니다(SPOILER_MEDIA, 기본값 groups, 다른 값은 always와 never). /report는 메시지를 소유자에게 전달합니다. SpicyAPI의 규칙을 위반하는 콘텐츠는 spicyapi.ai/abuse에서도 신고할 수 있습니다.
문제 해결
| 메시지 또는 증상 | 해결 방법 |
|---|---|
"out of balance"(40201) | SpicyAPI 잔액을 충전하세요. |
"reached the spend cap"(40202) | 콘솔에서 설정한 키의 한도에 도달했습니다. 한도를 올리거나 기다리세요. |
"not allowed to use that model"(40301) | 콘솔에서 키에 해당 모델을 허용하거나 /models로 다른 모델을 고르세요. |
"has not verified its email"(40310) | SpicyAPI에서 온 인증 링크를 여세요. |
| "The model declined this request" | 해당 모델이 프롬프트를 거부했습니다. 요청을 조정하거나 다른 모델을 선택하세요. 거부 시 과금 조건은 모델 페이지에서 확인하세요. |
Conflict: terminated by other getUpdates request | 같은 토큰을 쓰는 봇 사본이 둘입니다. 하나를 중지하세요. |
| Discord 명령이 보이지 않음 | /pic과 /vid는 연령 제한 채널에서만 표시됩니다. 전역 명령은 나타나기까지 잠시 걸릴 수 있으니, 즉시 등록하려면 DISCORD_GUILD_ID를 설정하세요. |
| 프록시 환경에서 네트워크 오류 | 봇을 NODE_USE_ENV_PROXY=1로 시작하지 않으면 Node의 fetch는 HTTPS_PROXY를 무시합니다. |
| 메시지를 보내면 봇이 숫자로 답함 | 내 사용자 ID입니다. OWNER_ID에 넣고 다시 시작하세요. |
오류 코드는 오류에 설명되어 있습니다.

