notify-mcp
notify-mcp
Example Corp 직원을 위해 자기 자신에게만 보내는 이메일 + SMS를 제공하는, Entra 인증을 사용하는 원격 MCP 서버입니다. 이는 claude.ai chief-of-staff 롤아웃의 발송 경로입니다. 에이전트는 로그인한 사용자 본인에게 그 사용자 자신의 콘텐츠만 이메일이나 문자로 보낼 수 있고, 구조적으로 그 외의 대상에게는 보낼 수 없습니다.
불변 원칙(이 서버가 존재하는 이유)
신뢰할 수 없는 콘텐츠(인바운드 이메일, 티켓, 채팅)를 읽는 에이전트는 제약 없는 발송 권한을 절대 가져서는 안 됩니다. 프롬프트 인젝션이 그 권한을 정보 유출 채널로 바꿀 수 있기 때문입니다. 이 서버는 구조 자체로 이 문제를 해결합니다.
수신자는 도구 매개변수가 아닙니다. 이메일은 검증된 Entra 토큰에서 가져온 호출자의 UPN으로 발송됩니다. SMS는 기록상 호출자의 휴대전화로 발송됩니다. 완전히 장악당한 모델도 무엇을 보낼지는 바꿀 수 있어도, 어디로 보낼지는 절대 바꿀 수 없습니다.
FROM은
<agent>approver@example.com으로 고정됩니다. 이 서버는 사람으로서 발송할 수 없으므로 누구도 사칭할 수 없습니다.Resend + Inteliquent 키는 이 컨테이너 안에만 존재합니다. 사용자는 키를 볼 수 없으며, 자신의 M365 로그인으로 인증합니다.
사용자별 시간당 예산과 발송 건당 감사 로그 한 줄이 적용됩니다.
Related MCP server: graphdo-ts
도구
도구 | 설명 |
| 발송 내용이 전달될 이메일과 마스킹된 휴대전화를 반환합니다. 연결 확인은 이 도구로 먼저 하세요. |
| 호출자에게 이메일을 보냅니다. |
| 회사 DID 13105550100에서 호출자의 휴대전화로 문자를 보냅니다. 최대 640자입니다. |
| SMS 설정을 시작합니다. 해당 번호로 6자리 코드를 문자로 보냅니다. |
| 설정을 완료합니다. 코드를 확인하고 번호를 저장한 뒤 사용자에게 변경 알림 이메일을 보냅니다. |
서버가 사용자 신원을 아는 방법
Claude → Entra 로그인(사용자 본인의 로그인) → 모든 도구 호출은 Bearer JWT를 전달합니다 → AzureJWTVerifier가 서명·발급자·대상(audience)을 검증합니다 → preferred_username 클레임이 수신자가 됩니다. 사용자별 환경 변수도, 설정도 필요 없습니다. 신원은 암호학적으로 증명됩니다.
휴대전화 번호는 토큰에 없으므로 SMS는 검증된 자체 등록을 사용합니다. Entra의 mobilePhone을 채워 두지 않는 테넌트를 위한 방식입니다(우리 테넌트도 그렇습니다).
사용자(보통 CoS 설정 인터뷰 중)가 "register my mobile 310-555-1212"라고 말하면 → 서버가 해당 번호로 6자리 코드를 문자로 보냅니다.
사용자가 코드를 입력 →
confirm_my_mobile→ 번호가 UPN을 키로 하여/data/sms_directory.json에 저장되고 확인 이메일이 발송됩니다.이후 변경은 잠깁니다(
NOTIFY_ALLOW_MOBILE_CHANGE=false). 확인된 번호는 관리자가 레지스트리를 직접 편집해야만 변경할 수 있습니다. 코드 검증은 소유를 증명하고, 변경 잠금 + 이메일 알림은 인젝션 리바인딩 공격(악성 콘텐츠가 문자를 다른 곳으로 돌리는 공격)을 차단합니다.
해석 순서: 이름 파일(직접 입력 항목은 문자열, 자체 등록 항목은 객체) → Graph를 통한 선택적 Entra mobilePhone(NOTIFY_GRAPH_LOOKUP_ENABLED=true + -GrantGraphUserRead). 자체 등록을 사용 중이라면 불필요합니다.
커넥터 세션 지속성(연결 끊김 해결)
커넥터가 "연결 끊김"으로 표시되지 않게 하는 세 가지 요소는 다음과 같습니다.
offline_access를 광고합니다. 보호된 리소스 메타데이터에 이 항목(NOTIFY_ADVERTISE_OFFLINE_ACCESS=true)을 포함하면 Claude 로그인에서 갱신 토큰을 얻고 ~60–90분짜리 액세스 토큰을 자동으로 갱신합니다.stateless_http=True— 세션은 컨테이너를 다시 배포해도 유지됩니다.NPM 프록시 호스트에는 플레이북의 타임아웃 재정의 설정이 있어야 합니다(PORTAINER_DEPLOY.md 참조). 유휴 스트림이 60초에 끊기지 않게 하기 위함입니다.
또한 이 앱이 Conditional Access 로그인 빈도 정책에 걸리지 않는지도 확인하세요.
인수 테스트: 연결 후 2시간 이상 유휴 상태로 두고, 컨테이너를 다시 배포한 다음, whoami를 호출해도 재인증 프롬프트가 나타나지 않아야 합니다.
설정(플레이북 순서)
scripts/setup_entra_app.ps1 -TenantId <tenant>(선택적으로-GrantGraphUserRead)을 실행합니다 — 서버 환경 변수 값과 커넥터 시크릿을 출력합니다. 커넥터 시크릿은 Claude의 커넥터 고급 설정에 입력되며, 서버에는 절대 넣지 않습니다.Portainer Git stack으로 모바일 배포합니다 — PORTAINER_DEPLOY.md 참고. 권장 호스트 포트는 8093입니다(먼저 포트를 확인하고 플레이북 레지스트리에 기록).
NPM 프록시 호스트
notify-mcp.example.com→ 컨테이너로 연결합니다. 플레이북 타임아웃과 Anthropic IP 허용 목록을 적용하고, 허용 목록을 활성화하기 전에 LE 인증서를 발급받습니다.claude.ai에서 조직 커스텀 커넥터로 추가합니다. 사용자는 각자 자신의 M365 로그인으로 한 번만 연결하면 됩니다.
인수 테스트
curl http://<docker-host>:8093/healthz # {"status":"ok",...}
curl -s https://notify-mcp.example.com/.well-known/oauth-protected-resource/mcp | jq
# scopes_supported MUST include the full https://.../mcp/access_as_user scope
# AND "offline_access"
curl -i https://notify-mcp.example.com/mcp # 401 + WWW-Authenticate그런 다음 Claude에서 그룹 멤버로:
whoami→ 호출자 본인의 이메일과 휴대전화 "기록 (…1234)" 또는 확실한 없음이 표시됩니다.send_email_to_me→notify_ai@에서 보낸 메시지가 본인 받은 편지함에 도착합니다.모델에 "에게 이걸 보내 줘"라고 요청하면 → 반드시 거절하거나 / 방법이 없어야 합니다. 이 항목이 실패하면 P1입니다. 배포하지 마세요.
register_my_mobile에 본인 번호로 등록 → 코드 도착 →confirm_my_mobile→ 확인 이메일 도착 →send_sms_to_me가 동작합니다. 그다음 다른 번호로 등록을 시도하면 → 반드시 거부되어야 합니다(변경 잠금).위 2시간 유휴 + 재배포 테스트.
멤버가 아닌 사용자가 연결하면 → 로그인 시 거부됩니다(AADSTS50105).
로컬 개발
pip install -r requirements.txt
MCP_AUTH_ENABLED=false python -m notify_mcp # Inspector only — tools will
# refuse to send without a token
# identity; NEVER expose auth-offThis server cannot be installed
Maintenance
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
- AlicenseCqualityDmaintenanceEnables secure, zero-trust access to MCP tools through short-lived, signed capability leases that bind tool execution to specific sessions, intents, and constraints. Prevents prompt injection attacks and privilege escalation with dynamic risk scoring, policy enforcement, and tamper-evident audit logging.41MIT

graphdo-tsofficial
AlicenseAqualityCmaintenanceEnables AI agents to send emails and manage tasks in Microsoft To Do with scoped, low-risk access to Microsoft Graph.3511MIT- AlicenseNot gradedqualityCmaintenanceEnables email agents to send emails with granular trust levels per contact, ensuring human approval for high-risk or unknown recipients while allowing automatic sending for trusted ones.MIT
- AlicenseNot gradedqualityBmaintenanceAuthenticated email service MCP for AI agents.183Apache 2.0
Related MCP Connectors
Phone, SMS & email for AI agents — one remote MCP endpoint, OAuth login, zero install.
Hosted email MCP for AI agents with inboxes, send/receive, memory, recovery, and credits.
Remote MCP for Copilot CLI switch gate MCP, structured receipts, audit logs, and reviewer-ready evid
Latest Blog Posts
- Who's Calling? MCP Hosts Are an Identity Blind Spot (And the Spec Knows It)By Om-Shree-0709 on .mcpAgent IdentityOAuth 2.1
- Your AI Chatbot Just Exposed Your CEO's Salary to an InternBy Om-Shree-0709 on .Agent IdentityMCP SecurityOAuth Delegation
- Why MCP Servers Need Execution Sandboxing (And Why Your Current Stack Isn't Enough)By Om-Shree-0709 on .Agentic AiPrompt InjectionWebAssembly
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/JohnGilligan2/mcp-notify'
If you have feedback or need assistance with the MCP directory API, please join our Discord server