Skip to main content
Glama
4hmad69
by 4hmad69

SubTrack — 구독 및 정기 청구 추적기(MCP 서버)

해결하는 문제: 거의 모든 사람이 잊어버린 구독과 정기 청구로 조용히 돈을 흘려보내고 있습니다. 유료로 전환된 스트리밍 무료 체험, 헬스장 멤버십, 1년에 한 번 청구되고 11개월 동안 잊히는 도메인 갱신 비용 같은 것들입니다. SubTrack은 LLM(Claude 또는 모든 MCP 클라이언트)이 이를 모두 추적하고, 곧 갱신될 항목을 알려주며, 구독이 주간·월간·분기·연간 또는 사용자 지정 주기로 청구되더라도 월 단위 수치로 정규화된 총 지출을 보여줍니다.

기능

도구

용도

add_subscription

임의의 청구 주기를 가진 구독/청구 항목 추가

get_subscription

하나를 조회하고, 계산된 다음 갱신 날짜를 함께 반환

list_subscriptions

전체 목록 조회(또는 카테고리로 필터링), 갱신이 가장 임박한 순서대로

edit_subscription

기존 항목의 모든 필드 업데이트

cancel_subscription

소프트 삭제(비활성으로 표시, 기록은 유지)

delete_subscription

하드 삭제

upcoming_renewals

"다음 N일 안에 갱신되는 항목은?"

spending_summary

카테고리별 총 정기 지출, 월간/연간 기준으로 정규화

여기에 subtrack://categories 리소스(편집 가능한 카테고리 목록)와, 다가오는 항목에 대한 친근한 요약을 어시스턴트가 작성하도록 요청하는 renewal_digest_prompt 프롬프트 템플릿도 포함됩니다.

흥미로운 엔지니어링 포인트는 next_renewal_date()입니다. 이 함수는 일 단위 주기(주간/격주/사용자 지정)를 모듈러 연산으로 정확히 진행시키고, 달력 기반 주기(월간/분기/연간)는 실제 달력 월을 더하는 방식으로 처리합니다(1월 31일에 시작한 구독은 "31일 후"가 아니라 정확히 2월 28일에 도래합니다).

Related MCP server: subscription-tracker-mcp

도구가 async def인 이유

여기 있는 모든 도구는 async def이며, 모든 SQLite 접근은 표준 라이브러리 sqlite3 대신 aiosqlite를 통해 이루어집니다. 흔히 혼동되는 지점이므로 그 이유를 이해해 둘 가치가 있습니다:

  • FastMCP는 기본적으로 일반 def 도구를 스레드 풀에서 실행하므로, 이 서버의 동기 버전도 가벼운 부하에서는 실제로 멈추지 않을 것입니다.

  • 하지만 async def 안에서 블로킹 드라이버(sqlite3)를 사용하는 것은 동기 방식을 유지하는 것보다 더 나쁩니다. FastMCP는 async def 도구를 스레드로 오프로드하지 않으며(이벤트 루프에서 직접 실행), 따라서 그 안의 블로킹 호출은 다른 모든 동시 요청을 지연시키기 때문입니다.

  • 따라서 도구를 def로 유지해 프레임워크가 스레드 오프로드하도록 하거나, async def로 작성하면서 그리고 끝까지 진정한 비동기 드라이버를 사용해야 합니다. 이 서버는 후자를 선택했으며, 이는 여러 클라이언트의 동시 도구 호출이 발생할 수 있는 원격 서버에 더 확장성 있는 패턴입니다. 진행 중인 DB 호출마다 작업자 스레드를 소비하지 않고, 나중에 다른 awaitable I/O(HTTP 호출 등)를 추가할 때도 깔끔하게 결합됩니다.

  • 단 하나의 예외: 작은 categories.json 읽기는 일반 동기 방식으로 유지됩니다. 호출당 몇 백 바이트를 한 번 읽는 것뿐이라, "비동기"로 만든다면 실제 동시성 이점 없이 aiofiles만 추가하게 됩니다.

프로젝트 구조

subtrack-mcp/
├── server.py          # the whole server — module-level `mcp` object
├── pyproject.toml     # project metadata + deps (managed by uv)
├── uv.lock            # locked, reproducible dependency versions
├── .python-version    # pins the Python version uv uses
├── .gitignore
└── README.md

categories.jsonsubscriptions.db는 커밋되지 않습니다. server.py가 첫 실행 시 자동으로 생성합니다(init_categories() / init_db() 참조). 재배포 후에도 자신만의 고정 카테고리 목록을 유지하려면 .gitignore에서 categories.json을 제거하고 편집한 버전을 커밋하세요.

로컬에서 실행하기 (uv)

수동 venv 단계는 필요 없습니다. uv run은 처음 사용할 때 uv.lock에서 .venv를 자동으로 생성하고 동기화합니다.

server.py__main__ 블록은 기본적으로 0.0.0.0:8000에서 HTTP로 서버를 실행합니다(PORT 환경 변수로 재정의 가능). 이는 FastMCP Cloud가 프로덕션에서 사용하는 것과 동일한 전송 방식이므로, 로컬 테스트가 실제 배포 환경과 일치합니다:

uv run server.py
# Starting MCP server 'SubTrack' with transport 'http' on http://0.0.0.0:8000/mcp

참고: 이 블록은 파일을 직접 실행할 때만 동작합니다. FastMCP Cloud는 이를 완전히 무시합니다. mcp 객체를 가져와 자체적으로 서빙하므로, 여기의 어떤 내용도 배포된 서버에 영향을 주지 않습니다.

간단한 클라이언트 스크립트로 테스트해 보세요(uv run python client_test.py):

import asyncio
from fastmcp import Client

async def main():
    async with Client("http://127.0.0.1:8000/mcp") as client:
        result = await client.call_tool("add_subscription", {
            "name": "Netflix", "amount": 15.99, "billing_cycle": "monthly",
            "start_date": "2026-08-05", "category": "Streaming", "subcategory": "Video"
        })
        print(result.data)

asyncio.run(main())

대신 stdio를 기대하는 MCP 클라이언트로 테스트하려면(예: 로컬 사용을 위해 Claude Desktop에 연결), __main__의 내용과 관계없이 전송 방식을 재정의하는 FastMCP CLI를 통해 실행하세요:

uv run fastmcp run server.py:mcp --transport stdio

의존성 추가 또는 업데이트

pyproject.toml의 의존성 목록을 직접 수정하지 마세요. uv.lock이 동기화된 상태를 유지하도록 uv가 관리하게 하세요:

uv add some-package             # add a new dependency
uv add some-package --upgrade   # bump one dependency
uv lock --upgrade               # re-resolve everything to latest compatible versions

FastMCP Cloud에 배포

  1. 이 폴더를 GitHub 저장소에 푸시하세요. pyproject.toml uv.lock을 커밋하세요(.venv/는 커밋하지 마세요. gitignore에 포함되어 있습니다).

  2. fastmcp.cloud에 GitHub로 로그인하고 저장소에서 새 프로젝트를 만드세요.

  3. 엔트리포인트를 다음으로 설정하세요:

    server.py:mcp
  4. 배포하세요. FastMCP Cloud는 pyproject.toml에서 의존성을 자동으로 감지합니다(일반 requirements.txt도 이해하지만, 여기서는 필요 없습니다). 그러면 https://<project>.fastmcp.app/mcp 같은 URL을 받게 되며, 모든 MCP 클라이언트 — 사용자 지정 커넥터를 통한 Claude를 포함해 — 가 호출할 수 있습니다.

스토리지에 관한 참고 사항

이 서버는 단순함을 위해 로컬 디스크의 SQLite를 사용합니다. 학습용과 단일 인스턴스 배포에는 훌륭하지만, 대부분의 관리형 플랫폼에서는 재배포 후에도 유지된다는 보장이 없습니다(새로 배포하면 보통 새 파일시스템이 생깁니다). 도구 로직이 마음에 들면, 자연스러운 다음 단계이자 원격 MCP 서버를 더 배우기 좋은 연습은 sqlite3를 호스팅 데이터베이스(Turso/libSQL, asyncpg를 통한 Postgres, Supabase 등)로 교체하고, 연결 문자열을 FastMCP Cloud 대시보드에서 설정한 환경 변수(os.getenv("DATABASE_URL"))로 사용하는 것입니다.

확장 아이디어

  • renewal_digest_prompt 출력을 사용해 다이제스트를 이메일/푸시로 보내는 mcp.tool()을 추가하세요.

  • price_history 테이블과 시간에 따른 가격 인상을 기록하는 도구를 추가하세요.

  • 서버를 공개 대신 비공개로 전환할 준비가 되면 인증(FastMCP는 베어러 토큰 인증 지원)을 추가하세요.

F
license - not found
Not graded
quality - not tested
B
maintenance

Maintenance

Maintainers
Response time
Release cycle
Releases (12mo)
Commit activity

Resources

Unclaimed servers have limited discoverability.

Looking for Admin?

If you are the server author, to access and configure the admin panel.

Related MCP Servers

  • A
    license
    B
    quality
    C
    maintenance
    Enables personal finance management through Budgetsco, supporting transaction tracking, budget management, recurring transactions, custom categories, and multi-currency support for comprehensive financial tracking.
    18
    14
    MIT
  • F
    license
    A
    quality
    C
    maintenance
    An MCP-powered AI agent that audits your Gmail for recurring subscriptions, detects silent price increases, and flags unused services.
    6

View all related MCP servers

Related MCP Connectors

View all MCP Connectors

Latest Blog Posts

MCP directory API

We provide all the information about MCP servers via our MCP API.

curl -X GET 'https://glama.ai/api/mcp/v1/servers/4hmad69/subtrack-mcp'

If you have feedback or need assistance with the MCP directory API, please join our Discord server